cgma
|
00001 00002 #ifndef DYNAMIC_TREE_ITERATOR_HPP 00003 #define DYNAMIC_TREE_ITERATOR_HPP 00004 00005 #include <functional> 00006 #include <algorithm> 00007 #include "CubitDefines.h" 00008 #include "DynamicDLIIterator.hpp" 00009 00010 // use this functor to iterate over first items in a map 00011 template <class Pair, class First> 00012 struct MapSelect1st : public std::unary_function<Pair, First> 00013 { 00014 const First& operator()(const Pair& x) const 00015 { 00016 return x.first; 00017 } 00018 }; 00019 00020 // use this functor to iterate over second items in a map 00021 template <class Pair, class Second> 00022 struct MapSelect2nd : public std::unary_function<Pair, Second> 00023 { 00024 const Second& operator()(const Pair& x) const 00025 { 00026 return x.second; 00027 } 00028 }; 00029 00030 // use this functor to iterate over items in a set 00031 template <class Item> 00032 struct SetSelect : public std::unary_function<Item, Item> 00033 { 00034 const Item& operator()(const Item& x) const 00035 { 00036 return x; 00037 } 00038 }; 00039 00040 template <class TreeType, class Y, class Which> struct TreeSelectFind 00041 : public std::unary_function<typename TreeType::value_type, bool> 00042 { 00043 Y* mToFind; 00044 TreeSelectFind(Y* y) : mToFind(y) {} 00045 bool operator()(const typename TreeType::value_type& comp) const 00046 { 00047 return mToFind == Which()(comp); 00048 } 00049 }; 00050 00051 // TreeType is a set, map, or multimap, OutType is whatever type DynamicDLIIterator needs to return 00052 // and Which is one of MapSelect1st, MapSelect2nd, SetSelect, or whatever you want 00053 // for example 00054 // typedef std::set<CubitEntity*> MySet; 00055 // MySet the_set; 00056 // DynamicTreeIterator<MySet, CubitEntity, SetSelect<MySet::value_type> >* iter = 00057 // new DynamicTreeIterator<MySet, CubitEntity, SetSelect<MySet::value_type> >; 00058 // iter->watch(the_set); 00059 00060 template < class TreeType, class OutType, class Which > class DynamicTreeIterator 00061 : public DynamicDLIIterator<OutType> 00062 { 00063 public: 00064 DynamicTreeIterator() : mTree(0) {} 00065 ~DynamicTreeIterator(){} 00066 00067 void watch(TreeType& the_tree) 00068 { 00069 mTree = &the_tree; 00070 mIter = mTree->begin(); 00071 } 00072 00073 virtual void reset() 00074 { 00075 mIter = mTree->begin(); 00076 } 00077 00078 virtual void step(int n = 1) 00079 { 00080 if(mTree->empty()) 00081 return; 00082 while(n--) 00083 { 00084 if(++mIter == mTree->end()) 00085 mIter = mTree->begin(); 00086 } 00087 } 00088 00089 virtual unsigned int size() const 00090 { 00091 return mTree->size(); 00092 } 00093 virtual OutType* get() const 00094 { 00095 if(mTree->empty()) 00096 return NULL; 00097 return Which()(*mIter); 00098 } 00099 virtual OutType* next(int n = 1) const 00100 { 00101 if(mTree->empty()) 00102 return NULL; 00103 typename TreeType::iterator iter = mIter; 00104 while(n--) 00105 { 00106 if(++iter == mTree->end()) 00107 iter = mTree->begin(); 00108 } 00109 return Which()(*iter); 00110 } 00111 virtual OutType* get_and_step(int n = 1) 00112 { 00113 OutType* tmp = get(); 00114 step(n); 00115 return tmp; 00116 } 00117 00118 virtual CubitBoolean move_to(OutType* item) 00119 { 00120 typename TreeType::iterator iter = find_item(item); 00121 if(iter != mTree->end()) 00122 { 00123 mIter = iter; 00124 return CUBIT_TRUE; 00125 } 00126 return CUBIT_FALSE; 00127 } 00128 00129 virtual CubitBoolean is_in_list(OutType* item) const 00130 { 00131 return find_item(item) != mTree->end(); 00132 } 00133 virtual CubitBoolean is_at_end() const 00134 { 00135 if(mTree->empty()) 00136 return CUBIT_TRUE; 00137 typename TreeType::iterator iter = mIter; 00138 ++iter; 00139 return iter == mTree->end(); 00140 } 00141 virtual CubitBoolean is_at_beginning() const 00142 { 00143 return mTree->begin() == mIter; 00144 } 00145 virtual DynamicDLIIterator<OutType>* clone() const 00146 { 00147 DynamicTreeIterator<TreeType, OutType, Which>* new_iterator = new DynamicTreeIterator<TreeType, OutType, Which>; 00148 *new_iterator = *this; 00149 return new_iterator; 00150 } 00151 00152 private: 00153 typename TreeType::iterator find_item(OutType* item) const 00154 { 00155 typename TreeType::iterator iter = std::find_if(mIter, mTree->end(), 00156 TreeSelectFind<TreeType, OutType, Which>(item)); 00157 if(iter == mTree->end()) 00158 { 00159 iter = std::find_if(mTree->begin(), mIter, 00160 TreeSelectFind<TreeType, OutType, Which>(item)); 00161 if(iter == mIter) 00162 iter = mTree->end(); 00163 } 00164 return iter; 00165 } 00166 TreeType* mTree; 00167 typename TreeType::iterator mIter; 00168 }; 00169 00170 #endif // DYNAMIC_TREE_ITERATOR_HPP 00171