PolyBoRi
|
00001 // -*- c++ -*- 00002 //***************************************************************************** 00070 //***************************************************************************** 00071 00072 // include basic definitions 00073 #include "pbori_defs.h" 00074 00075 // include polybori functionals 00076 #include "pbori_func.h" 00077 00078 #include "BooleSet.h" 00079 00080 #ifndef CTermGenerator_h_ 00081 #define CTermGenerator_h_ 00082 00083 BEGIN_NAMESPACE_PBORI 00084 00085 00086 template <class TermType, class BehaviourTag = type_tag<TermType> > 00087 class CTermGeneratorBase; 00088 00089 #if 0 00090 template <class TermType> 00091 class CTermGeneratorBase<TermType, type_tag<BooleMonomial> >{ 00092 00093 public: 00094 typedef TermType value_type; 00095 typedef value_type result_type; 00096 00097 template <class SequenceType> 00098 result_type operator()(const SequenceType& seq) const{ 00099 00100 value_type result(!seq.isZero()); 00101 00102 typename SequenceType::stack_reverse_iterator 00103 start(seq.stackRBegin()), finish(seq.stackREnd()); 00104 00105 #ifndef PBORI_NO_TERMS_BY_TAIL 00106 typename BooleSet::navigator navi(result.diagram().navigation()); 00107 00108 assert((start == finish) || !start->isConstant()); 00109 while((start != finish) && 00110 (start->elseBranch().isEmpty()) && (start->thenBranch() == navi) ) { 00111 navi = *start; 00112 ++start; 00113 } 00114 00115 result = value_type(BooleSet(navi)); 00116 #endif 00117 00118 while (start != finish){ 00119 result.changeAssign(**start); 00120 ++start; 00121 } 00122 00123 return result; 00124 } 00125 }; 00126 #endif //if0 00127 00128 class BooleExponent; 00129 template <class TermType> 00130 class CTermGeneratorBase<TermType, type_tag<BooleExponent> > { 00131 00132 public: 00133 typedef TermType value_type; 00134 typedef value_type result_type; 00135 00136 template <class SequenceType> 00137 result_type operator()(const SequenceType& seq) const{ 00138 00139 value_type result; 00140 result.reserve(seq.deg()); 00141 typename SequenceType::const_iterator 00142 start(seq.begin()), finish(seq.end()); 00143 00144 while (start != finish){ 00145 result.push_back(*start); 00146 ++start; 00147 } 00148 return result; 00149 } 00150 }; 00151 00152 template <class TermType> 00153 class CTermGeneratorBase<TermType, type_tag<CTypes::size_type> > { 00154 public: 00155 typedef TermType value_type; 00156 typedef value_type result_type; 00157 00158 template <class SequenceType> 00159 result_type operator()(const SequenceType& seq) const{ 00160 return seq.deg(); 00161 } 00162 }; 00163 00164 00165 template <class TermType> 00166 class CTermGeneratorBase<TermType, type_tag<CTypes::deg_type> > { 00167 public: 00168 typedef TermType value_type; 00169 typedef value_type result_type; 00170 00171 template <class SequenceType> 00172 result_type operator()(const SequenceType& seq) const{ 00173 return seq.deg(); 00174 } 00175 }; 00176 00177 template <class TermType> 00178 class CTermGenerator: 00179 public CTermGeneratorBase<TermType> { 00180 public: 00181 typedef CTermGeneratorBase<TermType> base; 00182 00183 typedef CTypes::dd_type dd_type; 00184 typedef dd_type::core_type data_type; 00185 00186 CTermGenerator(const data_type&): base() {} 00187 CTermGenerator(const CTermGenerator& rhs): base(rhs) {} 00188 CTermGenerator(): base() {} 00189 00190 }; 00191 00193 class NoData {}; 00194 00195 00196 template <class TermType, class BehaviourTag = type_tag<TermType> > 00197 class MyCTermGeneratorBase; 00198 00199 template <class TermType> 00200 class CTermGeneratorBase<TermType, type_tag<BooleMonomial> >{ 00201 00202 public: 00203 typedef TermType value_type; 00204 typedef value_type result_type; 00205 00206 typedef CTypes::manager_base manager_base; 00207 00208 typedef CTypes::dd_type dd_type; 00209 typedef dd_type::core_type data_type; 00210 00211 // typedef CTypes::manager_base data_type; 00212 data_type m_data; 00214 00215 CTermGeneratorBase(const data_type& data): m_data(data) {} 00216 00217 CTermGeneratorBase(): m_data() {} 00218 00219 template <class SequenceType> 00220 result_type operator()(const SequenceType& seq) const { 00221 assert(m_data != data_type()); 00222 00223 // Do not dereference empty sequence (corresponds to end()) 00224 assert(!seq.isZero()); 00225 00226 // @todo: avoid using manager_base here 00227 typedef typename value_type::ring_type ring_type; 00228 typedef typename ring_type::manager_type manager_type; 00229 value_type result((ring_type)manager_type(m_data)); 00230 00231 typename SequenceType::stack_reverse_iterator 00232 start(seq.stackRBegin()), finish(seq.stackREnd()); 00233 00234 #ifndef PBORI_NO_TERMS_BY_TAIL 00235 typename BooleSet::navigator navi(result.diagram().navigation()); 00236 00237 assert((start == finish) || !start->isConstant()); 00238 while((start != finish) && 00239 (start->elseBranch().isEmpty()) && (start->thenBranch() == navi) ) { 00240 navi = *start; 00241 ++start; 00242 } 00243 00244 result = value_type(dd_type(m_data, navi)); 00245 #endif 00246 00247 while (start != finish){ 00248 result.changeAssign(**start); 00249 ++start; 00250 } 00251 00252 return result; 00253 } 00254 }; 00255 00256 00257 template <> 00258 class CTermGenerator<BooleMonomial>: 00259 public CTermGeneratorBase<BooleMonomial> { 00260 public: 00261 typedef BooleMonomial term_type; 00262 typedef CTermGeneratorBase<term_type> base; 00263 typedef base::data_type data_type; 00264 00265 CTermGenerator(const data_type& data): base(data) {} 00266 CTermGenerator(const CTermGenerator& rhs): base(rhs) {} 00267 CTermGenerator(): base() {} 00268 }; 00269 00270 END_NAMESPACE_PBORI 00271 00272 #endif