00001
00002
00151
00152
00153 #ifndef BooleMonomial_h_
00154 #define BooleMonomial_h_
00155
00156
00157 #include "pbori_defs.h"
00158
00159
00160 #include "BoolePolynomial.h"
00161 #include "BooleVariable.h"
00162
00163 #include <map>
00164
00165
00166 #include "CVariableIter.h"
00167
00168
00169 #include "PBoRiError.h"
00170
00171 BEGIN_NAMESPACE_PBORI
00172
00173 class BooleVariable;
00174 class BooleExponent;
00175 template <class DDType, class MonomType> class CDDOperations;
00176
00185 class BooleMonomial {
00186
00187 public:
00188 template <class, class> friend class CDDOperations;
00189 friend class COrderBase;
00190 template <class, class> friend class CTermGeneratorBase;
00191
00192
00193
00194
00195
00197
00198 typedef CTypes::dd_type dd_type;
00199 typedef CTypes::size_type size_type;
00200 typedef CTypes::idx_type idx_type;
00201 typedef CTypes::hash_type hash_type;
00202 typedef CTypes::bool_type bool_type;
00203 typedef CTypes::comp_type comp_type;
00204 typedef CTypes::integer_type integer_type;
00205 typedef CTypes::ostream_type ostream_type;
00207
00209 typedef BooleMonomial self;
00210
00212 typedef BoolePolynomial poly_type;
00213
00215 typedef poly_type::var_type var_type;
00216
00218 typedef poly_type::constant_type constant_type;
00219
00221 typedef poly_type::set_type set_type;
00222
00224 typedef poly_type::exp_type exp_type;
00225
00227 typedef poly_type::ring_type ring_type;
00228
00230 typedef poly_type::first_iterator const_iterator;
00231
00233 typedef CVariableIter<const_iterator, var_type> variable_iterator;
00234
00236
00237
00238 typedef std::map<self, idx_type, symmetric_composition<
00239 std::less<poly_type::navigator>,
00240 navigates<poly_type> > > idx_map_type;
00241
00243 typedef dd_type::easy_equality_property easy_equality_property;
00244
00246 BooleMonomial():
00247 m_poly( BooleEnv::one() ) { }
00248
00250 BooleMonomial(const self& rhs):
00251 m_poly(rhs.m_poly) {}
00252
00254 BooleMonomial(const var_type& rhs);
00255
00256
00258 BooleMonomial(const exp_type& rhs, const ring_type& ring):
00259 m_poly(rhs, ring) { }
00260
00262 BooleMonomial(const ring_type& ring):
00263 m_poly(ring.one()) {}
00264
00266 ~BooleMonomial() {}
00267
00269 operator const BoolePolynomial&() const { return m_poly; }
00270
00272 exp_type exp() const;
00273
00274
00276 const_iterator begin() const { return m_poly.firstBegin(); }
00277
00279 const_iterator end() const { return m_poly.firstEnd(); }
00280
00282 variable_iterator variableBegin() const {
00283 return variable_iterator(begin(), ring());
00284 }
00285
00287 variable_iterator variableEnd() const {
00288 return variable_iterator(end(), ring());
00289 }
00290
00292 size_type deg() const {
00294 #if 0
00295 return m_poly.nNodes();
00296 #else
00297 return std::distance(m_poly.firstBegin(),m_poly.firstEnd());
00298 #endif
00299 }
00300
00302 size_type size() const { return deg(); }
00303
00305 set_type divisors() const { return m_poly.lmDivisors(); }
00306
00308 set_type multiples(const self&) const;
00309
00311 hash_type stableHash() const {
00312 return stable_first_hash_range(m_poly.navigation());
00313 }
00314
00316 hash_type hash() const { return m_poly.hash(); }
00317
00319 self& changeAssign(idx_type);
00320
00322 self change(idx_type) const;
00323
00324
00326
00327 self& operator*=(const self&);
00328 self& operator/=(const self&);
00329 self& operator*=(const var_type&);
00330 self& operator/=(const var_type&);
00332
00334
00335 bool_type operator==(const self& rhs) const { return m_poly == rhs.m_poly; }
00336 bool_type operator!=(const self& rhs) const { return m_poly != rhs.m_poly; }
00337 bool_type operator==(constant_type rhs) const { return m_poly == rhs; }
00338 bool_type operator!=(constant_type rhs) const { return m_poly != rhs; }
00339 bool_type isOne() const { return m_poly.isOne(); }
00340 bool_type isConstant() const { return m_poly.isConstant(); }
00342
00344 bool_type reducibleBy(const self& rhs) const {
00345 return m_poly.reducibleBy(rhs); }
00346 bool_type reducibleBy(const var_type& rhs) const;
00347
00349 comp_type compare(const self&) const;
00350
00352 size_type LCMDeg(const self&) const;
00353
00355 self& LCMAssign(const self&);
00356
00358 self LCM(const self&) const;
00359
00361 self& GCDAssign(const self&);
00362
00364 self GCD(const self&) const;
00365
00367 const dd_type& diagram() const { return m_poly.diagram(); }
00368
00370 set_type set() const { return m_poly.set(); }
00371
00373 self& popFirst() {
00374 assert(!m_poly.isConstant());
00375 return *this = set_type( dd_type(m_poly.diagram().manager(),
00376 m_poly.navigation().thenBranch()) );
00377 }
00378
00380 var_type firstVariable() const;
00381
00383 idx_type firstIndex() const {
00384 assert(!m_poly.isConstant());
00385 return *begin();
00386 }
00387
00389 ring_type ring() const { return m_poly.ring(); }
00390
00391 protected:
00393 dd_type& internalDiagram() { return m_poly.internalDiagram(); }
00394
00396
00398 BooleMonomial(const set_type& rhs): m_poly(rhs.diagram()) {
00399 assert(!m_poly.isZero());
00400 }
00401
00402 private:
00403 BoolePolynomial m_poly;
00404 };
00405
00407 inline BooleMonomial
00408 operator*(const BooleMonomial& lhs, const BooleMonomial& rhs) {
00409 return BooleMonomial(lhs) *= rhs;
00410 }
00412 inline BooleMonomial
00413 operator*(const BooleMonomial& lhs, const BooleVariable& rhs) {
00414 return BooleMonomial(lhs) *= rhs;
00415 }
00417 inline BoolePolynomial
00418 operator*(const BooleMonomial& lhs, BooleConstant rhs) {
00419 return BoolePolynomial(lhs) *= rhs;
00420 }
00421
00423 inline BoolePolynomial
00424 operator*(BooleConstant lhs, const BooleMonomial& rhs) {
00425 return rhs * lhs;
00426 }
00427
00429 inline BooleMonomial
00430 operator/(const BooleMonomial& lhs, const BooleMonomial& rhs) {
00431 return BooleMonomial(lhs) /= rhs;
00432 }
00433
00435 inline BooleMonomial
00436 operator/(const BooleMonomial& lhs, const BooleVariable& rhs) {
00437 return lhs / BooleMonomial(rhs);
00438 }
00439
00441 inline BooleMonomial::bool_type
00442 operator<(const BooleMonomial& lhs, const BooleMonomial& rhs) {
00443
00444 return (lhs.compare(rhs) == CTypes::less_than);
00445 }
00446
00448 inline BooleMonomial::bool_type
00449 operator>(const BooleMonomial& lhs, const BooleMonomial& rhs) {
00450
00451 return (lhs.compare(rhs) == CTypes::greater_than);
00452 }
00453
00455 inline BooleMonomial::bool_type
00456 operator<=(const BooleMonomial& lhs, const BooleMonomial& rhs) {
00457
00458 return (lhs.compare(rhs) <= CTypes::less_or_equal_max);
00459 }
00460
00462 inline BooleMonomial::bool_type
00463 operator>=(const BooleMonomial& lhs, const BooleMonomial& rhs) {
00464
00465 return (lhs.compare(rhs) >= CTypes::greater_or_equal_min);
00466 }
00467
00468
00470 inline BooleMonomial
00471 GCD(const BooleMonomial& lhs, const BooleMonomial& rhs ){
00472
00473 return lhs.GCD(rhs);
00474 }
00475
00477 inline BooleMonomial
00478 LCM(const BooleMonomial& lhs, const BooleMonomial& rhs ){
00479
00480 return lhs.LCM(rhs);
00481 }
00482
00485 BooleMonomial::bool_type
00486 greater_variable(BooleMonomial::idx_type lhs, BooleMonomial::idx_type rhs);
00487
00488
00490 inline BoolePolynomial
00491 operator*(const BooleVariable& lhs, const BooleConstant& rhs){
00492
00493 return BooleMonomial(lhs) * rhs;
00494 }
00495
00497 inline BoolePolynomial
00498 operator*(const BooleConstant& lhs, const BooleVariable& rhs){
00499
00500 return rhs * lhs;
00501 }
00502
00504 inline BoolePolynomial
00505 operator*(const BooleVariable& lhs,
00506 const BoolePolynomial& rhs){
00507
00508 return BoolePolynomial(rhs) *= BooleMonomial(lhs);
00509 }
00510
00512 inline BooleMonomial
00513 operator*(const BooleVariable& lhs,
00514 const BooleMonomial& rhs){
00515
00516 return BooleMonomial(lhs) * rhs;
00517 }
00518
00520 inline BoolePolynomial&
00521 operator*=(BoolePolynomial& lhs,
00522 const BooleVariable& rhs){
00523
00524 return lhs *= BooleMonomial(rhs);
00525 }
00526
00528 inline BooleMonomial
00529 operator*(const BooleVariable& lhs,
00530 const BooleVariable& rhs){
00531
00532 return BooleMonomial(lhs) *= BooleMonomial(rhs);
00533 }
00534
00536 inline BoolePolynomial
00537 operator*(const BoolePolynomial& lhs,
00538 const BooleVariable& rhs){
00539
00540 return BoolePolynomial(lhs) *= BooleMonomial(rhs);
00541 }
00542
00544 inline BoolePolynomial&
00545 operator/=(BoolePolynomial& lhs, const BooleVariable& rhs){
00546
00547 return lhs /= BooleMonomial(rhs);
00548 }
00549
00551 inline BoolePolynomial
00552 operator/(const BoolePolynomial& lhs,
00553 const BooleVariable& rhs){
00554
00555 return lhs / BooleMonomial(rhs);
00556 }
00557
00558
00560 inline BoolePolynomial
00561 operator%(const BoolePolynomial& lhs,
00562 const BooleVariable& rhs){
00563
00564 return lhs % BooleMonomial(rhs);
00565 }
00566
00568 inline BoolePolynomial&
00569 operator%=(BoolePolynomial& lhs,
00570 const BooleVariable& rhs){
00571
00572 return lhs %= BooleMonomial(rhs);
00573 }
00574
00575 END_NAMESPACE_PBORI
00576
00577
00578 #endif // of BooleMonomial_h_