00001
00002
00039
00040
00041
00042 #include <stack>
00043 #include <utility>
00044
00045
00046 #include "pbori_defs.h"
00047
00048
00049 #include "CTermIter.h"
00050
00051
00052 #ifndef CBidirectTermIter_h_
00053 #define CBidirectTermIter_h_
00054
00055 BEGIN_NAMESPACE_PBORI
00056
00057 template<class NavigatorType>
00058 class handle_else :
00059 public std::deque<NavigatorType> {
00060 public:
00061
00062 typedef NavigatorType navigator_type;
00063 typedef std::deque<NavigatorType> base;
00064
00065 void operator()(const navigator_type& navi) {
00066
00067 while(!base::empty() && (*top() >= *navi) )
00068 base::pop_back();
00069
00070 base::push_back(navi);
00071 }
00072 void push(const navigator_type& navi) { base::push_back(navi); }
00073 void pop() { base::pop_back(); }
00074
00075 const navigator_type& top() const { return base::back(); };
00076
00077 void append(const handle_else& rhs) {
00078 assert(base::empty() || rhs.empty() || ((**rhs.begin()) > (*top())) );
00079 base::insert(base::end(), rhs.begin(), rhs.end());
00080 }
00081 };
00082
00083 #if 0
00084
00090 template <class TermType, class NavigatorType,
00091 class ForwardOp, class BackwardOp,
00092 class TerminalValueOp = project_ith<2> >
00093 class CBidirectTermIter:
00094 public CTermIter<TermType, NavigatorType,
00095 ForwardOp, BackwardOp,
00096 TerminalValueOp,
00097 handle_else<NavigatorType> >{
00098
00099 public:
00100
00102 typedef TermType term_type;
00103
00105 typedef NavigatorType navigator_type;
00106
00108 typedef ForwardOp forwardop_type;
00109
00111 typedef BackwardOp backwardop_type;
00112
00114 typedef TerminalValueOp termvalop_type;
00115
00117 typedef handle_else<navigator_type> elsehandle_type;
00118
00120 typedef CBidirectTermIter<term_type, navigator_type,
00121 forwardop_type, backwardop_type, termvalop_type> self;
00122
00124 typedef CTermIter<term_type, navigator_type,
00125 forwardop_type, backwardop_type, termvalop_type,
00126 elsehandle_type> base;
00127
00129
00130 typedef std::bidirectional_iterator_tag iterator_category;
00131 typedef typename base::difference_type difference_type;
00132 typedef typename base::pointer pointer;
00133 typedef typename base::reference reference;
00135
00137 using base::handleElse;
00138
00140 CBidirectTermIter():
00141 base() {}
00142
00144 CBidirectTermIter(navigator_type navi,
00145 forwardop_type fop_ = forwardop_type(),
00146 backwardop_type bop_ = backwardop_type(),
00147 termvalop_type tvop_ = termvalop_type() ):
00148 base(navi, fop_, bop_, tvop_) {}
00149
00151 CBidirectTermIter(navigator_type navi, dummy_iterator):
00152 base() {
00153 if(navi.isValid()) {
00154 followElse(navi);
00155 terminate(navi);
00156 }
00157 }
00158
00160 CBidirectTermIter(const self& rhs):
00161 base(rhs) {};
00162
00164 ~CBidirectTermIter() {};
00165
00167 self& operator++() {
00168 base::operator++();
00169 return *this;
00170 }
00171
00173 self operator++(int dummy) {
00174 return base::operator++(dummy);
00175 };
00176
00178 self& operator--() {
00179
00180 if (!handleElse.empty()){
00181 navigator_type navi = handleElse.top();
00182 base::popToIndex(*navi);
00183
00184
00185 handleElse.pop();
00186 base::nextThen(navi);
00187
00188 followElse(navi);
00189 }
00190 else
00191 base::clear();
00192 return *this;
00193 }
00194
00196 self operator--(int) {
00197 self tmp(*this);
00198 operator--();
00199 return tmp;
00200 };
00201
00202 protected:
00203
00204
00205 void followElse(navigator_type& navi) {
00206 while( !navi.isConstant() ) {
00207 if(!navi.elseBranch().isEmpty()) {
00208 handleElse.push(navi);
00209 navi.incrementElse();
00210 }
00211 else
00212 base::nextThen(navi);
00213 }
00214 }
00215
00216 };
00217
00218 #endif
00219
00220 END_NAMESPACE_PBORI
00221
00222 #endif