[mathicgb] 318/393: Removed FreeModuleOrder from PolyBasis and GroebnerBasis as well as all the code that uses the order from those. Also removed most of the code from FreeModuleOrder.

Doug Torrance dtorrance-guest at moszumanska.debian.org
Fri Apr 3 15:59:28 UTC 2015


This is an automated email from the git hooks/post-receive script.

dtorrance-guest pushed a commit to branch upstream
in repository mathicgb.

commit 4a48b0a6c7fdbdf7df52a9f4753cf7270e46f93e
Author: Bjarke Hammersholt Roune <bjarkehr.code at gmail.com>
Date:   Sat May 11 16:18:14 2013 +0200

    Removed FreeModuleOrder from PolyBasis and GroebnerBasis as well as all the code that uses the order from those. Also removed most of the code from FreeModuleOrder.
---
 Makefile.am                      |   3 +-
 src/cli/SigGBAction.cpp          |   7 +-
 src/mathicgb/Basis.cpp           |   2 +-
 src/mathicgb/Basis.hpp           |   3 +-
 src/mathicgb/BuchbergerAlg.cpp   |   3 +-
 src/mathicgb/DivLookup.hpp       |  15 +-
 src/mathicgb/FreeModuleOrder.cpp | 321 +--------------------------------------
 src/mathicgb/FreeModuleOrder.hpp |  11 --
 src/mathicgb/GroebnerBasis.cpp   |  34 ++---
 src/mathicgb/GroebnerBasis.hpp   |  32 ++--
 src/mathicgb/PairTriangle.cpp    |   7 +-
 src/mathicgb/PolyBasis.cpp       |   4 +-
 src/mathicgb/PolyBasis.hpp       |  13 +-
 src/mathicgb/SigSPairQueue.cpp   | 182 +++++++++++++++++++++-
 src/mathicgb/SigSPairQueue.hpp   |   8 +-
 src/mathicgb/SigSPairs.cpp       |   4 +-
 src/mathicgb/SignatureGB.cpp     |   2 +-
 src/mathicgb/TypicalReducer.cpp  |   6 +-
 src/test/F4MatrixBuilder.cpp     |   5 +-
 19 files changed, 256 insertions(+), 406 deletions(-)

diff --git a/Makefile.am b/Makefile.am
index 2e4e4e1..11b2192 100755
--- a/Makefile.am
+++ b/Makefile.am
@@ -106,8 +106,7 @@ check_PROGRAMS=$(TESTS)
 unittest_LDADD = $(DEPS_LIBS) $(top_builddir)/libmathicgb.la
 
 test_LIBS=
-unittest_SOURCES=src/test/FreeModuleOrderTest.cpp			\
-  src/test/gtestInclude.cpp src/test/testMain.cpp			\
+unittest_SOURCES= src/test/gtestInclude.cpp src/test/testMain.cpp	\
   src/test/gb-test.cpp src/test/ideals.cpp src/test/poly-test.cpp	\
   src/test/ideals.hpp src/test/SparseMatrix.cpp				\
   src/test/QuadMatrixBuilder.cpp src/test/F4MatrixBuilder.cpp		\
diff --git a/src/cli/SigGBAction.cpp b/src/cli/SigGBAction.cpp
index f1d95a2..14eaee6 100755
--- a/src/cli/SigGBAction.cpp
+++ b/src/cli/SigGBAction.cpp
@@ -10,12 +10,11 @@
 #include <iostream>
 
 SigGBAction::SigGBAction():
-  mUseSingularCriterionEarly("earlySingularCriterion",
+  mUseSingularCriterionEarly(
+    "earlySingularCriterion",
     "Apply the singular S-pair elimination criterion before queueing "
     "that S-pair. Otherwise, the criterion is only checked just before "
-    "the S-pair would otherwise cause a polynomial reduction to occur. "
-    "This criterion is only relevant to the signature Buchberger "
-    "algorithm.",
+    "the S-pair would otherwise cause a polynomial reduction to occur. ",
     false),
 
   mPostponeKoszul("postponeKoszul",
diff --git a/src/mathicgb/Basis.cpp b/src/mathicgb/Basis.cpp
index 006b76d..9e3c201 100755
--- a/src/mathicgb/Basis.cpp
+++ b/src/mathicgb/Basis.cpp
@@ -15,7 +15,7 @@ void Basis::insert(std::unique_ptr<Poly>&& p) {
   mGenerators.push_back(std::move(p));
 }
 
-void Basis::sort(FreeModuleOrder& order) {
+void Basis::sort() {
   const auto& monoid = ring().monoid();
   const auto cmp = [&monoid](
     const std::unique_ptr<Poly>& a,
diff --git a/src/mathicgb/Basis.hpp b/src/mathicgb/Basis.hpp
index c8981b3..3afbf11 100755
--- a/src/mathicgb/Basis.hpp
+++ b/src/mathicgb/Basis.hpp
@@ -9,7 +9,6 @@
 #include <vector>
 
 class Poly;
-class FreeModuleOrder;
 
 // Really: a list of polynomials
 // BUT ALSO maybe: includes memory areas for the polynomials?
@@ -37,7 +36,7 @@ public:
   bool empty() const {return mGenerators.empty();}
   void reserve(size_t size) {mGenerators.reserve(size);}
 
-  void sort(FreeModuleOrder& order);
+  void sort();
 
 private:
   Basis(const Basis&); // not available
diff --git a/src/mathicgb/BuchbergerAlg.cpp b/src/mathicgb/BuchbergerAlg.cpp
index 0c6b69d..d5aa751 100755
--- a/src/mathicgb/BuchbergerAlg.cpp
+++ b/src/mathicgb/BuchbergerAlg.cpp
@@ -26,7 +26,7 @@ BuchbergerAlg::BuchbergerAlg(
   mRing(*basis.getPolyRing()),
   mOrder(FreeModuleOrder::makeOrder(0, *basis.getPolyRing())), // todo: remove
   mReducer(reducer),
-  mBasis(mRing, *mOrder, DivisorLookup::makeFactory(
+  mBasis(mRing, DivisorLookup::makeFactory(
     *basis.getPolyRing(),
     divisorLookupType)->create(preferSparseReducers, true)
   ),
@@ -326,7 +326,6 @@ size_t BuchbergerAlg::getMemoryUse() const {
 }
 
 void BuchbergerAlg::printStats(std::ostream& out) const {
-  out << " term order:         " << mBasis.order().description() << '\n';
   out << " reduction type:     " << mReducer.description() << '\n';
   out << " divisor tab type:   " << mBasis.divisorLookup().getName() << '\n';
   out << " S-pair queue type:  " << mSPairs.name() << '\n';
diff --git a/src/mathicgb/DivLookup.hpp b/src/mathicgb/DivLookup.hpp
old mode 100644
new mode 100755
index 2e6d619..8764d38
--- a/src/mathicgb/DivLookup.hpp
+++ b/src/mathicgb/DivLookup.hpp
@@ -456,7 +456,7 @@ private:
             // ensures deterministic behavior.
             const const_monomial minSig = mSigBasis.getSignature(mMinLeadGen);
             const const_monomial genSig = mSigBasis.getSignature(entry.index);
-            int sigCmp = mSigBasis.order().signatureCompare(minSig, genSig);
+            int sigCmp = mSigBasis.monoid().compare(minSig, genSig);
             MATHICGB_ASSERT(sigCmp != EQ); // no two generators have same signature
             if (sigCmp == GT)
               return true;
@@ -621,17 +621,6 @@ public:
         _finder.insert(Entry(mon, val));
   }
 
-#if 0
-  virtual bool findDivisor(const_monomial sig, const_monomial mon, size_t &val, monomial &result_multiplier)
-  {
-        DO out(getConfiguration().order(), getConfiguration().getPolyRing(), sig, mon, val, result_multiplier);
-        _finder.findAllDivisors(mon, out);
-        return out.found();
-  }
-#endif
-  // ifdef the above code to 0 and this to 1, if you wish to use: choose divisor to be a one wih minimal number
-  // of monomial that satisfies sig and divisibility criteria.
-#if 1
   virtual size_t regularReducer(const_monomial sig, const_monomial mon) const
   {
     DOCheckAll out(
@@ -643,7 +632,7 @@ public:
     _finder.findAllDivisors(mon, out);
     return out.reducer();
   }
-#endif
+
   unsigned long long getExpQueryCount() const {
     return _finder.getConfiguration().getExpQueryCount();
   }
diff --git a/src/mathicgb/FreeModuleOrder.cpp b/src/mathicgb/FreeModuleOrder.cpp
index 9999f36..06eef39 100755
--- a/src/mathicgb/FreeModuleOrder.cpp
+++ b/src/mathicgb/FreeModuleOrder.cpp
@@ -13,215 +13,12 @@
 #include <limits>
 #include <stdexcept>
 
-// In this file we define various term orders. Some classes need to be
-// specialized to each term order which we do using templates. Those
-// classes are defined here since they should not be used from
-// anywhere else - instead they should be accessed through their
-// virtual interface.
-
-// *******************************************************
-// ** Utility objects
-
-namespace {
-  template<class Cmp>
-  class Comparer {
-  public:
-    Comparer(const Cmp& cmp): mCmp(cmp), mComparisons(0) {}
-    bool operator()(const PreSPair& a, const PreSPair& b) const {
-      ++mComparisons;
-      return mCmp.signatureCompare(a.signature, b.signature) == LT;
-    }
-    size_t comparisons() const {return mComparisons;}
-  private:
-    const Cmp& mCmp;
-    mutable size_t mComparisons;
-  };
-
-  // Iterator that accesses the field i based on a passed-in iterator.
-  template<class PairIterator>
-  class IndexIterator {
-  public:
-
-	typedef typename PairIterator::iterator_category iterator_category;
-    typedef decltype(reinterpret_cast<typename PairIterator::value_type*>(0)->i) value_type;
-	typedef typename PairIterator::difference_type difference_type;
-	typedef value_type* pointer;
-	typedef value_type& reference;
-
-	IndexIterator(PairIterator pairIterator): mIterator(pairIterator) {}
-	IndexIterator& operator++() {++mIterator; return *this;}
-    const value_type operator*() const {return mIterator->i;}
-	difference_type operator-(const IndexIterator<PairIterator>& it) const {
-	  return mIterator - it.mIterator;
-	}
-	bool operator==(const IndexIterator<PairIterator>& it) const {
-	  return mIterator == it.mIterator;
-	}
-	bool operator!=(const IndexIterator<PairIterator>& it) const {
-	  return mIterator != it.mIterator;
-	}
-
-  private:
-	PairIterator mIterator;
-  };
-}
-
-// *******************************************************
-// ** SigSPairQueue
-namespace {
-  // Configuration of mathic::PairTriangle for use with signature queues.
-  template<class Cmp>
-  class SigPTConfiguration {
-  public:
-	SigPTConfiguration
-    (GroebnerBasis const& basis, Cmp const& cmp): mBasis(basis), mCmp(cmp) {}
-
-	typedef monomial PairData;
-	void computePairData(size_t col, size_t row, monomial sig) {
-      MATHICGB_ASSERT(mBasis.ratioCompare(col, row) != EQ);
-      // ensure that ratio(col) > ratio(row)
-      if (mBasis.ratioCompare(col, row) == LT)
-        std::swap(col, row);
-      mBasis.ring().monomialFindSignature
-        (mBasis.getLeadMonomial(col),
-         mBasis.getLeadMonomial(row),
-         mBasis.getSignature(col), sig);
-    }
-
-	typedef bool CompareResult;
-	bool compare(int colA, int rowA, const_monomial a,
-				 int colB, int rowB, const_monomial b) const {
-      return mCmp.signatureCompare(b, a) == LT;
-	}
-	bool cmpLessThan(bool v) const {return v;}
-
-    GroebnerBasis const& basis() const {return mBasis;}
-    Cmp const& comparer() const {return mCmp;}
-
-  private:
-    GroebnerBasis const& mBasis;
-    Cmp const& mCmp;
-  };
-
-  // Object that stores S-pairs and orders them according to a monomial
-  // or signature.
-  template<class Cmp>
-  class ConcreteSigSPairQueue : public SigSPairQueue {
-  public:
-    ConcreteSigSPairQueue(GroebnerBasis const& basis, Cmp const& cmp):
-      mPairQueue(PC(basis, cmp)) {}
-
-    virtual monomial popSignature(Pairs& pairs) {
-      pairs.clear();
-      if (mPairQueue.empty())
-        return 0;
-      monomial sig = ring().allocMonomial();
-      ring().monomialCopy(mPairQueue.topPairData(), sig);
-      do {
-        pairs.push_back(mPairQueue.topPair());
-        mPairQueue.pop();
-      } while
-          (!mPairQueue.empty() && ring().monomialEQ(mPairQueue.topPairData(), sig));
-      return sig;
-    }
-
-    virtual void pushPairs(size_t pairWith, IndexSigs& pairs) {
-#ifdef DEBUG
-      monomial tmp = ring().allocMonomial();
-      for (size_t i = 0; i < pairs.size(); ++i) {
-        MATHICGB_ASSERT(pairs[i].i < columnCount());
-        mPairQueue.configuration().computePairData
-          (columnCount(), pairs[i].i, tmp);
-        MATHICGB_ASSERT(ring().monomialEQ(tmp, pairs[i].signature));
-      }
-      ring().freeMonomial(tmp);
-#endif
-
-      if (columnCount() >= std::numeric_limits<BigIndex>::max())
-        throw std::overflow_error
-          ("Too large basis element index in constructing S-pairs.");
-    
-      // sort and insert new column
-      Comparer<Cmp> cmp(comparer());
-      std::sort(pairs.begin(), pairs.end(), cmp);
-      //mPreComparisons += cmp.comparisons();
-      //order().destructiveSort(pairs);
-      typedef IndexIterator<std::vector<PreSPair>::const_iterator> Iter;
-      mPairQueue.addColumnDescending(Iter(pairs.begin()), Iter(pairs.end()));
-    
-      // free signatures
-      std::vector<PreSPair>::iterator end = pairs.end();
-      for (std::vector<PreSPair>::iterator it = pairs.begin(); it != end; ++it)
-        ring().freeMonomial(it->signature);
-      pairs.clear();
-    }
-  
-    virtual std::string name() const {return "todo";}
-
-    virtual size_t memoryUse() const {return mPairQueue.getMemoryUse();}
-
-    virtual size_t pairCount() const {return mPairQueue.pairCount();}
-
-    virtual size_t columnCount() const {return mPairQueue.columnCount();}
-
-  private:
-    ConcreteSigSPairQueue(const ConcreteSigSPairQueue<Cmp>&); // not available
-    void operator=(const ConcreteSigSPairQueue<Cmp>&); // not available
-
-    // the compiler should be able to resolve these accessors into a direct
-    // offset as though these were member variables.
-    const GroebnerBasis& basis() const {
-      return mPairQueue.configuration().basis();
-    }
-    const Cmp& comparer() const {return mPairQueue.configuration().comparer();}
-    PolyRing const& ring() const {return basis().ring();}
-    FreeModuleOrder const& order() const {return basis().order();}
-
-    typedef SigPTConfiguration<Cmp> PC;
-    mathic::PairQueue<PC> mPairQueue;
-    friend struct mathic::PairQueueNamespace::ConstructPairDataFunction<PC>;
-    friend struct mathic::PairQueueNamespace::DestructPairDataFunction<PC>;
-  };
-}
-
-namespace mathic {
-  namespace PairQueueNamespace {
-	template<class Cmp>
-    struct ConstructPairDataFunction<SigPTConfiguration<Cmp> > {
-      inline static void function
-      (void* memory, Index col, Index row, SigPTConfiguration<Cmp>& conf) {
-        MATHICGB_ASSERT(memory != 0);
-        MATHICGB_ASSERT(col > row);
-        monomial* pd = new (memory) monomial
-          (conf.basis().ring().allocMonomial());
-        conf.computePairData(col, row, *pd);
-      }
-	};
-
-	template<class Cmp>
-    struct DestructPairDataFunction<SigPTConfiguration<Cmp> > {
-      inline static void function
-      (monomial* pd, Index col, Index row, SigPTConfiguration<Cmp>& conf) {
-        MATHICGB_ASSERT(pd != 0);
-        MATHICGB_ASSERT(col > row);
-        conf.basis().ring().freeMonomial(*pd);
-      }
-    };
-  }
-}
-
-// *******************************************************
-// ** Term orders
-
-template<class Cmp>
 class ConcreteOrder : public FreeModuleOrder {
 public:
-  ConcreteOrder(const PolyRing& ring): mCmp(ring), mComparisons(0), mPreComparisons(0) {}
-  virtual ~ConcreteOrder() {}
+  ConcreteOrder(const PolyRing& ring): mRing(ring) {}
 
   virtual int signatureCompare(const_monomial sigA, const_monomial sigB) const {
-    ++mComparisons;
-    return mCmp.signatureCompare(sigA, sigB);
+    return mRing.monomialCompare(sigA, sigB);
   }
 
   virtual int signatureCompare(
@@ -229,124 +26,18 @@ public:
     const_monomial monoB,
     const_monomial sigB
   ) const {
-    ++mComparisons;
-    return mCmp.signatureCompare(sigA, monoB, sigB);
-  }
-
-  virtual void sortSignatures(std::vector<PreSPair>& pairs) const {
-    Comparer<Cmp> cmp(mCmp);
-    std::sort(pairs.begin(), pairs.end(), cmp);
-    mPreComparisons += cmp.comparisons();
+    return mRing.monomialCompare(sigA, monoB, sigB);
   }
 
   virtual std::string description() const {
-    return mCmp.description();
-  }
-
-  virtual void getStats(size_t& comparisons, size_t& preComparisons) const {
-    comparisons = mComparisons;
-    preComparisons = mPreComparisons;
-  }
-
-  virtual std::unique_ptr<SigSPairQueue>
-  createSigSPairQueue(GroebnerBasis const& basis) const {
-    return std::unique_ptr<SigSPairQueue>
-      (new ConcreteSigSPairQueue<Cmp>(basis, mCmp));
+    return "todo";
   }
 
 private:
-  Cmp mCmp;
-  mutable size_t mComparisons;
-  mutable size_t mPreComparisons;
+  const PolyRing& mRing;
 };
 
-
-
-// ** Graded reverse lex.
-// Degrees and exponents considered from high index to low index.
-//
-//   rule: a[i] < b[i] then a > b
-//
-// also applies to component, which is considered last.
-class OrderA {
-public:
-  OrderA(const PolyRing& ring): mRing(&ring) {}
-
-  int signatureCompare(const_monomial sigA, const_monomial sigB) const {
-    return mRing->monomialCompare(sigA, sigB);
-  }
-
-  int signatureCompare(const_monomial sigA,
-    const_monomial monoB, const_monomial sigB) const {
-    return mRing->monomialCompare(sigA, monoB, sigB);
-  }
-
-  char const* description() const {return "GrevLex IndexDown";}
-
-private:
-  PolyRing const* const mRing;
-};
-
-class OrderC
-{
-public:
-  OrderC(const PolyRing& ring):
-    mRing(&ring), topindex(ring.maxMonomialSize() - 2)
-  {}
-
-  int signatureCompare(const_monomial sig, const_monomial sig2) const {
-    const auto d = sig[topindex] - sig2[topindex];
-    if (d < 0) return GT;
-    if (d > 0) return LT;
-
-    const auto cmp = *sig - *sig2;
-    if (cmp < 0) return GT;
-    if (cmp > 0) return LT;
-
-    return mRing->monomialCompare(sig, sig2);
-  }
-
-  int signatureCompare(
-    const_monomial sig,
-    const_monomial m2,
-    const_monomial sig2
-  ) const {
-    const auto d = sig[topindex] - (m2[topindex] + sig2[topindex]);
-    if (d < 0) return GT;
-    if (d > 0) return LT;
-
-    const auto cmp = *sig - *sig2;
-    if (cmp < 0) return GT;
-    if (cmp > 0) return LT;
-
-    return mRing->monomialCompare(sig, m2, sig2);
-  }
-
-  char const* description() const {return "DegreeUp IndexDown GrevLex";}
-
-private:
-  PolyRing const* const mRing;
-  const size_t topindex;
-};
-
-void FreeModuleOrder::displayOrderTypes(std::ostream &o)
-{
-  o << "FreeModule orders:" << std::endl;
-  o << "  1   GrevLex IndexDown" << std::endl;
-  o << "  2   DegreeUp IndexUp GrevLex" << std::endl; // done
-  o << "  3   DegreeUp IndexDown GrevLex" << std::endl;
-  o << "  4   SchreyerGrevLexUp" << std::endl; // done
-  o << "  5   SchreyerGrevLexDown" << std::endl; // done
-  o << "  6   IndexUp SchreyerGrevLex" << std::endl; // done
-  o << "  7   IndexDown SchreyerGrevLex" << std::endl; // done
-}
-
 std::unique_ptr<FreeModuleOrder> FreeModuleOrder::makeOrder(FreeModuleOrderType type, const PolyRing& ring)
 {
-  return make_unique<ConcreteOrder<OrderA>>(ring);
+  return make_unique<ConcreteOrder>(ring);
 }
-
-// Local Variables:
-// compile-command: "make -C .. "
-// indent-tabs-mode: nil
-// End:
diff --git a/src/mathicgb/FreeModuleOrder.hpp b/src/mathicgb/FreeModuleOrder.hpp
index 115e49f..1fd3a1a 100755
--- a/src/mathicgb/FreeModuleOrder.hpp
+++ b/src/mathicgb/FreeModuleOrder.hpp
@@ -27,21 +27,10 @@ public:
     const_monomial sig2
   ) const = 0;
 
-  // Sorts in ascending order of signature.
-  virtual void sortSignatures(std::vector<PreSPair>& pairs) const = 0;
-
-  virtual void getStats(size_t& comparisons, size_t& preComparisons) const = 0;
-
   virtual std::string description() const = 0;
 
-  virtual std::unique_ptr<SigSPairQueue>
-  createSigSPairQueue(GroebnerBasis const& basis) const = 0;
-
   /// @todo: We need at least an enum to make this clearer
   static std::unique_ptr<FreeModuleOrder> makeOrder(FreeModuleOrderType type, const PolyRing& ring);
-
-  static void displayOrderTypes(std::ostream &o);
-
 };
 
 #endif
diff --git a/src/mathicgb/GroebnerBasis.cpp b/src/mathicgb/GroebnerBasis.cpp
index a22d1f0..377c9ef 100755
--- a/src/mathicgb/GroebnerBasis.cpp
+++ b/src/mathicgb/GroebnerBasis.cpp
@@ -1,6 +1,5 @@
 // Copyright 2011 Michael E. Stillman
 
-#define MATHICGB_SLOW_DEBUG
 #include "stdinc.h"
 #include <iostream>
 #include <iomanip>
@@ -10,15 +9,14 @@
 
 GroebnerBasis::GroebnerBasis(
   const PolyRing* R0,
-  FreeModuleOrder* order,
   int divisorLookupType,
   int monTableType,
   bool preferSparseReducers):
   mDivisorLookupFactory
     (DivisorLookup::makeFactory(*R0, divisorLookupType)),
-  mRatioSorted(RatioOrder(sigLeadRatio, *order)),
+  mRatioSorted(RatioOrder(sigLeadRatio, R0->monoid())),
   mMinimalDivisorLookup(mDivisorLookupFactory->create(preferSparseReducers, true)),
-  mBasis(*R0, *order, mDivisorLookupFactory->create(preferSparseReducers, true)),
+  mBasis(*R0, mDivisorLookupFactory->create(preferSparseReducers, true)),
   mPreferSparseReducers(preferSparseReducers)
 {
   mTmp = mBasis.ring().allocMonomial();
@@ -147,7 +145,7 @@ again:
   mRatioRanks.push_back(rank);
   MATHICGB_ASSERT(mRatioRanks.size() == index + 1);
 
-#ifdef DEBUG
+#ifdef MATHICGB_DEBUG
     // Check that at least one space has been left between every rank
     MATHICGB_ASSERT(mRatioRanks[*mRatioSorted.begin()] > 0);
     MATHICGB_ASSERT(mRatioRanks[*mRatioSorted.rbegin()] <
@@ -178,7 +176,7 @@ size_t GroebnerBasis::regularReducer(
       (ring().monomialIsDivisibleBy(term, getLeadMonomial(reducer)));
     ring().monomialDivide(term, getLeadMonomial(reducer), m);
     ring().monomialMultTo(m, getSignature(reducer));
-    MATHICGB_SLOW_ASSERT(order().signatureCompare(sig, m) == GT);
+    MATHICGB_SLOW_ASSERT(monoid().lessThan(m, sig));
     ring().freeMonomial(m);
   }
 #endif
@@ -196,7 +194,7 @@ size_t GroebnerBasis::regularReducerSlow(
       continue;
     ring().monomialDivide(term, getLeadMonomial(be), m);
     ring().monomialMultTo(m, getSignature(be));
-    if (order().signatureCompare(sig, m) == GT) {
+    if (monoid().lessThan(m, sig)) {
       ring().freeMonomial(m);
       return be;
     }
@@ -215,7 +213,7 @@ void GroebnerBasis::lowBaseDivisors(
   const size_t component = ring().monomialGetComponent(sigNew);
   mSignatureLookup[component]->
     lowBaseDivisors(divisors, maxDivisors, newGenerator);
-#ifdef DEBUG
+#ifdef MATHICGB_DEBUG
   std::vector<size_t> debugValue;
   lowBaseDivisorsSlow(debugValue, maxDivisors, newGenerator);
   MATHICGB_ASSERT(divisors.size() <= maxDivisors);
@@ -265,7 +263,7 @@ void GroebnerBasis::lowBaseDivisorsSlow(
 size_t GroebnerBasis::highBaseDivisor(size_t newGenerator) const {
   MATHICGB_ASSERT(newGenerator < size());
   size_t highDivisor = divisorLookup().highBaseDivisor(newGenerator);
-#ifdef DEBUG
+#ifdef MATHICGB_DEBUG
   size_t debugValue = highBaseDivisorSlow(newGenerator);
   MATHICGB_ASSERT((highDivisor == static_cast<size_t>(-1)) ==
     (debugValue == static_cast<size_t>(-1)));
@@ -317,10 +315,10 @@ size_t GroebnerBasis::minimalLeadInSigSlow(const_monomial sig) const {
     ring().monomialDivide(sig, getSignature(gen), multiplier);
     if (minLeadGen != static_cast<size_t>(-1)) {
       const_monomial genLead = getLeadMonomial(gen);
-      int leadCmp = order().signatureCompare(minLead, multiplier, genLead);
-      if (leadCmp == LT)
+      const auto leadCmp = monoid().compare(minLead, multiplier, genLead);
+      if (leadCmp == Monoid::LessThan)
         continue;
-      if (leadCmp == EQ) {
+      if (leadCmp == Monoid::EqualTo) {
         // If same lead monomial in signature, pick the one with fewer terms
         // as that one might be less effort to reduce.
         const size_t minTerms = poly(minLeadGen).nTerms();
@@ -334,8 +332,10 @@ size_t GroebnerBasis::minimalLeadInSigSlow(const_monomial sig) const {
           // is less.
           const const_monomial minSig = getSignature(minLeadGen);
           const const_monomial genSig = getSignature(gen);
-          int sigCmp = order().signatureCompare(minSig, genSig);
-          MATHICGB_ASSERT(sigCmp != EQ); // no two generators have same signature
+          int sigCmp = monoid().compare(minSig, genSig);
+
+          // no two generators have same signature
+          MATHICGB_ASSERT(sigCmp != Monoid::EqualTo);
           if (sigCmp == GT)
             continue;
         }
@@ -363,7 +363,7 @@ bool GroebnerBasis::isSingularTopReducibleSlow
     if (!ring().monomialIsDivisibleBy(polyLead, getLeadMonomial(i)))
       continue;
     ring().monomialDivide(polyLead, getLeadMonomial(i), multiplier);
-    if (order().signatureCompare(sig, multiplier, getSignature(i)) == EQ)
+    if (monoid().compare(sig, multiplier, getSignature(i)) == EQ)
       return true;
   }
   ring().freeMonomial(multiplier);
@@ -451,10 +451,10 @@ size_t GroebnerBasis::ratioRank(const_monomial ratio) const {
       std::numeric_limits<Rank>::max());
     return std::numeric_limits<Rank>::max();
   } else {
-    if (order().signatureCompare(ratio, getSigLeadRatio(*pos)) == EQ)
+    if (monoid().equal(ratio, getSigLeadRatio(*pos)))
       return ratioRank(*pos);
     MATHICGB_ASSERT(ratioRank(*pos) > 0);
-#ifdef DEBUG
+#ifdef MATHICGB_DEBUG
     if (pos != mRatioSorted.begin()) {
       RatioSortedType::iterator prev = pos;
       --prev;
diff --git a/src/mathicgb/GroebnerBasis.hpp b/src/mathicgb/GroebnerBasis.hpp
index 5100106..5dad29e 100755
--- a/src/mathicgb/GroebnerBasis.hpp
+++ b/src/mathicgb/GroebnerBasis.hpp
@@ -7,7 +7,6 @@
 #include <set>
 #include "PolyRing.hpp"
 #include "Poly.hpp"
-#include "FreeModuleOrder.hpp"
 #include "DivisorLookup.hpp"
 #include "PolyBasis.hpp"
 #include "MonoProcessor.hpp"
@@ -18,19 +17,20 @@
 
 class GroebnerBasis {
 public:
+  typedef PolyRing::Monoid Monoid;
+
   GroebnerBasis(
     const PolyRing* R,
-    FreeModuleOrder* order,
     int divisorLookupType,
     int monTableType,
     bool preferSparseReducers
   );
   ~GroebnerBasis();
 
+  const Monoid& monoid() const {return ring().monoid();}
   const PolyRing& ring() const {return mBasis.ring();}
   const Poly& poly(size_t index) const {return mBasis.poly(index);}
   size_t size() const {return mBasis.size();}
-  const FreeModuleOrder& order() const {return mBasis.order();}
 
   // todo: stop using non-const version of basis() and then remove it.
   PolyBasis& basis() {return mBasis;}
@@ -165,19 +165,19 @@ private:
   std::vector<monomial> sigLeadRatio;
 
   // true if giving each generator an integer id based on its
-  // position in a sorted order of sig/lead ratios.
+  // position in a sorted order of sig-lead ratios.
   static const bool mUseRatioRank = USE_RATIO_RANK;
   static const bool mUseStoredRatioRank = USE_RATIO_RANK;
   class RatioOrder {
   public:
-    RatioOrder(std::vector<monomial>& ratio, const FreeModuleOrder& order):
-        mRatio(ratio), mOrder(order) {}
+    RatioOrder(std::vector<monomial>& ratio, const Monoid& monoid):
+      mRatio(ratio), mMonoid(monoid) {}
     bool operator()(size_t a, size_t b) const {
-      return mOrder.signatureCompare(mRatio[a], mRatio[b]) == LT;
+      return mMonoid.lessThan(mRatio[a], mRatio[b]);
     }
   private:
     std::vector<monomial>& mRatio;
-    const FreeModuleOrder& mOrder;
+    const Monoid& mMonoid;
   };
   typedef std::multiset<size_t, RatioOrder> RatioSortedType;
   typedef size_t Rank;
@@ -198,7 +198,7 @@ inline int GroebnerBasis::ratioCompare(size_t a, size_t b) const {
   if (mUseRatioRank) {
 #ifdef MATHICGB_DEBUG
     int const value =
-      order().signatureCompare(getSigLeadRatio(a), getSigLeadRatio(b));
+      monoid().compare(getSigLeadRatio(a), getSigLeadRatio(b));
 #endif
     if (mRatioRanks[a] < mRatioRanks[b]) {
       MATHICGB_ASSERT_NO_ASSUME(value == LT);
@@ -214,18 +214,18 @@ inline int GroebnerBasis::ratioCompare(size_t a, size_t b) const {
     // A/a < B/b   <=>  A < (B/b)a
     ring().monomialDivideToNegative(getSignature(b), getLeadMonomial(b), mTmp);
     ring().monomialMultTo(mTmp, getLeadMonomial(a));
-    int value = order().signatureCompare(getSignature(a), mTmp);
+    int value = monoid().compare(getSignature(a), mTmp);
     MATHICGB_ASSERT(value ==
-      order().signatureCompare(getSigLeadRatio(a), getSigLeadRatio(b)));
+      monoid().compare(getSigLeadRatio(a), getSigLeadRatio(b)));
     return value;
   }
 }
 
 inline int GroebnerBasis::StoredRatioCmp::compare(size_t be) const {
   if (GroebnerBasis::mUseStoredRatioRank) {
-#ifdef DEBUG
-    int value = mBasis.order().
-      signatureCompare(mRatio, mBasis.getSigLeadRatio(be));
+#ifdef MATHICGB_DEBUG
+    const auto value =
+      mBasis.monoid().compare(mRatio, mBasis.getSigLeadRatio(be));
 #endif
     GroebnerBasis::Rank otherRank = mBasis.ratioRank(be);
     if (mRatioRank < otherRank) {
@@ -240,9 +240,9 @@ inline int GroebnerBasis::StoredRatioCmp::compare(size_t be) const {
     }
   } else {
     mBasis.ring().monomialMult(mRatio, mBasis.getLeadMonomial(be), mTmp);
-    int value = mBasis.order().signatureCompare(mTmp, mBasis.getSignature(be));
+    int value = mBasis.monoid().compare(mTmp, mBasis.getSignature(be));
     MATHICGB_ASSERT(value ==
-      mBasis.order().signatureCompare(mRatio, mBasis.getSigLeadRatio(be)));
+      mBasis.monoid().compare(mRatio, mBasis.getSigLeadRatio(be)));
     return value;
   }
 }
diff --git a/src/mathicgb/PairTriangle.cpp b/src/mathicgb/PairTriangle.cpp
index 86119bc..bc89984 100755
--- a/src/mathicgb/PairTriangle.cpp
+++ b/src/mathicgb/PairTriangle.cpp
@@ -64,7 +64,12 @@ namespace {
 }
 
 void PairTriangle::endColumn() {
-  mOrder.sortSignatures(mPrePairs);
+  const auto& monoid = mRing.monoid();
+  const auto cmp = [&monoid](const PreSPair& a, const PreSPair& b) {
+    return monoid.lessThan(a.signature, b.signature);
+  };
+  std::sort(mPrePairs.begin(), mPrePairs.end(), cmp);
+
   typedef IndexIterator<std::vector<PreSPair>::const_iterator> Iter;
   mPairQueue.addColumnDescending
 	(Iter(mPrePairs.begin()), Iter(mPrePairs.end()));
diff --git a/src/mathicgb/PolyBasis.cpp b/src/mathicgb/PolyBasis.cpp
index 4ed5546..a7f2be5 100755
--- a/src/mathicgb/PolyBasis.cpp
+++ b/src/mathicgb/PolyBasis.cpp
@@ -6,11 +6,9 @@
 
 PolyBasis::PolyBasis(
   const PolyRing& ring,
-  FreeModuleOrder& order,
   std::unique_ptr<DivisorLookup> divisorLookup
 ):
   mRing(ring),
-  mOrder(order),
   mDivisorLookup(std::move(divisorLookup))
 {
   MATHICGB_ASSERT(mDivisorLookup.get() != 0);
@@ -37,7 +35,7 @@ std::unique_ptr<Basis> PolyBasis::initialIdeal() const {
       basis->insert(std::move(p));
     }
   }
-  basis->sort(mOrder);
+  basis->sort();
   return basis;
 }
 
diff --git a/src/mathicgb/PolyBasis.hpp b/src/mathicgb/PolyBasis.hpp
index faaf360..37e6971 100755
--- a/src/mathicgb/PolyBasis.hpp
+++ b/src/mathicgb/PolyBasis.hpp
@@ -8,16 +8,17 @@
 
 class PolyRing;
 class Basis;
-class FreeModuleOrder;
 
 class PolyBasis {
 public:
-  // Ring and order must live for as long as this object. divisorLookupFactory
+  typedef PolyRing::Monoid Monoid;
+
+  // Ring must live for as long as this object. divisorLookupFactory
   // only needs to live for the duration of the constructor.
   PolyBasis(
     const PolyRing& ring,
-    FreeModuleOrder& order,
-    std::unique_ptr<DivisorLookup> divisorLookup);
+    std::unique_ptr<DivisorLookup> divisorLookup
+  );
 
   // Deletes the Poly's stored in the basis.
   ~PolyBasis();
@@ -67,8 +68,7 @@ public:
   // Returns the ambient polynomial ring of the polynomials in the basis.
   const PolyRing& ring() const {return mRing;}
 
-  // Returns the term order on the basis.
-  const FreeModuleOrder& order() const {return mOrder;}
+  const Monoid& monoid() const {return ring().monoid();}
 
   // Returns a data structure containing the lead monomial of each lead
   // monomial.
@@ -219,7 +219,6 @@ private:
   typedef EntryCont::const_iterator EntryCIter;
 
   const PolyRing& mRing;
-  FreeModuleOrder& mOrder;
   std::unique_ptr<DivisorLookup> mDivisorLookup;
   std::vector<Entry> mEntries;
 };
diff --git a/src/mathicgb/SigSPairQueue.cpp b/src/mathicgb/SigSPairQueue.cpp
index 8def30e..d7859c4 100755
--- a/src/mathicgb/SigSPairQueue.cpp
+++ b/src/mathicgb/SigSPairQueue.cpp
@@ -1,5 +1,185 @@
 #include "stdinc.h"
 #include "SigSPairQueue.hpp"
 
-SigSPairQueue::~SigSPairQueue() {
+#include "GroebnerBasis.hpp"
+
+SigSPairQueue::~SigSPairQueue() {}
+
+namespace {
+  class Comparer {
+  public:
+    typedef PolyRing::Monoid Monoid;
+
+    Comparer(const Monoid& monoid): mMonoid(monoid) {}
+    bool operator()(const PreSPair& a, const PreSPair& b) const {
+      return mMonoid.lessThan(a.signature, b.signature);
+    }
+  private:
+    const Monoid& mMonoid;
+  };
+
+  // Iterator that accesses the field i based on a passed-in iterator.
+  template<class PairIterator>
+  class IndexIterator {
+  public:
+    
+    typedef typename PairIterator::iterator_category iterator_category;
+    typedef decltype(reinterpret_cast<typename PairIterator::value_type*>(0)->i) value_type;
+    typedef typename PairIterator::difference_type difference_type;
+    typedef value_type* pointer;
+    typedef value_type& reference;
+    
+    IndexIterator(PairIterator pairIterator): mIterator(pairIterator) {}
+    IndexIterator& operator++() {++mIterator; return *this;}
+    const value_type operator*() const {return mIterator->i;}
+    difference_type operator-(const IndexIterator<PairIterator>& it) const {
+      return mIterator - it.mIterator;
+    }
+    bool operator==(const IndexIterator<PairIterator>& it) const {
+      return mIterator == it.mIterator;
+    }
+    bool operator!=(const IndexIterator<PairIterator>& it) const {
+      return mIterator != it.mIterator;
+    }
+    
+  private:
+    PairIterator mIterator;
+  };
+}
+
+
+class ConcreteSigSPairQueue : public SigSPairQueue {
+public:
+  ConcreteSigSPairQueue(GroebnerBasis const& basis):
+  mPairQueue(Configuration(basis)) {}
+
+  virtual monomial popSignature(Pairs& pairs) {
+    pairs.clear();
+    if (mPairQueue.empty())
+      return 0;
+    monomial sig = ring().allocMonomial();
+    ring().monomialCopy(mPairQueue.topPairData(), sig);
+    do {
+      pairs.push_back(mPairQueue.topPair());
+      mPairQueue.pop();
+    } while
+        (!mPairQueue.empty() && ring().monomialEQ(mPairQueue.topPairData(), sig));
+    return sig;
+  }
+
+  virtual void pushPairs(size_t pairWith, IndexSigs& pairs) {
+#ifdef DEBUG
+    monomial tmp = ring().allocMonomial();
+    for (size_t i = 0; i < pairs.size(); ++i) {
+      MATHICGB_ASSERT(pairs[i].i < columnCount());
+      mPairQueue.configuration().computePairData
+        (columnCount(), pairs[i].i, tmp);
+      MATHICGB_ASSERT(ring().monomialEQ(tmp, pairs[i].signature));
+    }
+    ring().freeMonomial(tmp);
+#endif
+
+    if (columnCount() >= std::numeric_limits<BigIndex>::max())
+      throw std::overflow_error
+        ("Too large basis element index in constructing S-pairs.");
+    
+    // sort and insert new column
+    Comparer cmp(ring().monoid());
+    std::sort(pairs.begin(), pairs.end(), cmp);
+    typedef IndexIterator<std::vector<PreSPair>::const_iterator> Iter;
+    mPairQueue.addColumnDescending(Iter(pairs.begin()), Iter(pairs.end()));
+    
+    // free signatures
+    std::vector<PreSPair>::iterator end = pairs.end();
+    for (std::vector<PreSPair>::iterator it = pairs.begin(); it != end; ++it)
+      ring().freeMonomial(it->signature);
+    pairs.clear();
+  }
+  
+  virtual std::string name() const {return "todo";}
+
+  virtual size_t memoryUse() const {return mPairQueue.getMemoryUse();}
+
+  virtual size_t pairCount() const {return mPairQueue.pairCount();}
+
+  virtual size_t columnCount() const {return mPairQueue.columnCount();}
+
+private:
+  ConcreteSigSPairQueue(const ConcreteSigSPairQueue&); // not available
+  void operator=(const ConcreteSigSPairQueue&); // not available
+
+  // Configuration of mathic::PairTriangle for use with signature queues.
+  class Configuration {
+  public:
+    Configuration(GroebnerBasis const& basis): mBasis(basis) {}
+
+    typedef monomial PairData;
+    void computePairData(size_t col, size_t row, monomial sig) {
+      MATHICGB_ASSERT(mBasis.ratioCompare(col, row) != EQ);
+      // ensure that ratio(col) > ratio(row)
+      if (mBasis.ratioCompare(col, row) == LT)
+        std::swap(col, row);
+      mBasis.ring().monomialFindSignature
+        (mBasis.getLeadMonomial(col),
+         mBasis.getLeadMonomial(row),
+         mBasis.getSignature(col), sig);
+    }
+
+    typedef bool CompareResult;
+    bool compare(int colA, int rowA, const_monomial a,
+                 int colB, int rowB, const_monomial b) const {
+      return mBasis.ring().monoid().lessThan(b, a);
+    }
+    bool cmpLessThan(bool v) const {return v;}
+
+    GroebnerBasis const& basis() const {return mBasis;}
+
+  private:
+    GroebnerBasis const& mBasis;
+  };
+
+  // the compiler should be able to resolve these accessors into a direct
+  // offset as though these were member variables.
+  const GroebnerBasis& basis() const {
+    return mPairQueue.configuration().basis();
+  }
+  PolyRing const& ring() const {return basis().ring();}
+
+  mathic::PairQueue<Configuration> mPairQueue;
+  friend struct
+  mathic::PairQueueNamespace::ConstructPairDataFunction<Configuration>;
+  friend struct
+  mathic::PairQueueNamespace::DestructPairDataFunction<Configuration>;
+};
+
+namespace mathic {
+  namespace PairQueueNamespace {
+    template<>
+    struct ConstructPairDataFunction<ConcreteSigSPairQueue::Configuration> {
+      inline static void function
+      (void* memory, Index col, Index row, ConcreteSigSPairQueue::Configuration& conf) {
+        MATHICGB_ASSERT(memory != 0);
+        MATHICGB_ASSERT(col > row);
+        monomial* pd = new (memory) monomial
+          (conf.basis().ring().allocMonomial());
+        conf.computePairData(col, row, *pd);
+      }
+	};
+
+    template<>
+    struct DestructPairDataFunction<ConcreteSigSPairQueue::Configuration> {
+      inline static void function
+      (monomial* pd, Index col, Index row, ConcreteSigSPairQueue::Configuration& conf) {
+        MATHICGB_ASSERT(pd != 0);
+        MATHICGB_ASSERT(col > row);
+        conf.basis().ring().freeMonomial(*pd);
+      }
+    };
+  }
+}
+
+std::unique_ptr<SigSPairQueue> SigSPairQueue::create(
+  GroebnerBasis const& basis
+) {
+  return make_unique<ConcreteSigSPairQueue>(basis);
 }
diff --git a/src/mathicgb/SigSPairQueue.hpp b/src/mathicgb/SigSPairQueue.hpp
index 2ec34e1..3bba62d 100755
--- a/src/mathicgb/SigSPairQueue.hpp
+++ b/src/mathicgb/SigSPairQueue.hpp
@@ -13,14 +13,16 @@ struct PreSPair {
   monomial signature;
 };
 
+class GroebnerBasis;
+
 // A priority queue on S-pairs where the priority is based on a
 // signature as in signature Grobner basis algorithms. The class is
 // not responsible for eliminating S-pairs or doing anything beyond
 // order the S-pairs.
-//
-// You create these queues from a module term order.
 class SigSPairQueue {
 public:
+  typedef PolyRing::Monoid Monoid;
+
   virtual ~SigSPairQueue();
 
   typedef std::pair<size_t, size_t> Pair;
@@ -64,6 +66,8 @@ public:
 
   // Returns number of bytes of memory used.
   virtual size_t memoryUse() const = 0;
+
+  static std::unique_ptr<SigSPairQueue> create(GroebnerBasis const& basis);
 };
 
 #endif
diff --git a/src/mathicgb/SigSPairs.cpp b/src/mathicgb/SigSPairs.cpp
index dc95301..92759a8 100755
--- a/src/mathicgb/SigSPairs.cpp
+++ b/src/mathicgb/SigSPairs.cpp
@@ -27,8 +27,8 @@ SigSPairs::SigSPairs(
   GB(GB0),
   mReducer(reducer),
   mPostponeKoszuls(postponeKoszuls),
-  mQueue(GB->order().createSigSPairQueue(*GB)) {
-}
+  mQueue(SigSPairQueue::create(*GB))
+{}
 
 SigSPairs::~SigSPairs()
 {
diff --git a/src/mathicgb/SignatureGB.cpp b/src/mathicgb/SignatureGB.cpp
index de915a5..897592d 100755
--- a/src/mathicgb/SignatureGB.cpp
+++ b/src/mathicgb/SignatureGB.cpp
@@ -37,7 +37,7 @@ SignatureGB::SignatureGB(
   stats_relativelyPrimeEliminated(0),
   stats_pairsReduced(0),
   stats_nsecs(0.0),
-  GB(make_unique<GroebnerBasis>(R, F.get(), divlookup_type, montable_type, preferSparseReducers)),
+  GB(make_unique<GroebnerBasis>(R, divlookup_type, montable_type, preferSparseReducers)),
   mKoszuls(R->monoid()),
   Hsyz(MonomialTableArray::make(R, montable_type, basis.size(), !mPostponeKoszul)),
   Hsyz2(MonomialTableArray::make(R, montable_type, basis.size(), !mPostponeKoszul)),
diff --git a/src/mathicgb/TypicalReducer.cpp b/src/mathicgb/TypicalReducer.cpp
index 9fb2365..a6436a0 100755
--- a/src/mathicgb/TypicalReducer.cpp
+++ b/src/mathicgb/TypicalReducer.cpp
@@ -183,8 +183,10 @@ std::unique_ptr<Poly> TypicalReducer::classicReduce
 
     size_t reducer = basis.classicReducer(v.monom);
     if (reducer == static_cast<size_t>(-1)) { // no reducer found
-      MATHICGB_ASSERT(result->isZero() ||
-        basis.order().signatureCompare(v.monom, result->backMonomial()) == LT);
+      MATHICGB_ASSERT(
+        result->isZero() ||
+        basis.monoid().lessThan(v.monom, result->backMonomial())
+      );
       result->appendTerm(v.coeff, v.monom);
       removeLeadTerm();
     } else { // reduce by reducer
diff --git a/src/test/F4MatrixBuilder.cpp b/src/test/F4MatrixBuilder.cpp
index 93d62fc..0ac2828 100755
--- a/src/test/F4MatrixBuilder.cpp
+++ b/src/test/F4MatrixBuilder.cpp
@@ -3,7 +3,6 @@
 #include "mathicgb/Poly.hpp"
 #include "mathicgb/PolyRing.hpp"
 #include "mathicgb/F4MatrixBuilder.hpp"
-#include "mathicgb/FreeModuleOrder.hpp"
 #include "mathicgb/Basis.hpp"
 #include "mathicgb/PolyBasis.hpp"
 #include "mathicgb/io-util.hpp"
@@ -22,8 +21,7 @@ namespace {
     BuilderMaker():
       mRing(ringFromString("101 6 1\n1 1 1 1 1 1")),
       mIdeal(*mRing),
-      mOrder(FreeModuleOrder::makeOrder(1, *mIdeal.getPolyRing())),
-      mBasis(*mRing, *mOrder, DivisorLookup::makeFactory(*mRing, 1)->create(true, true)) {
+      mBasis(*mRing, DivisorLookup::makeFactory(*mRing, 1)->create(true, true)) {
     }
 
     const Poly& addBasisElement(const std::string& str) {
@@ -45,7 +43,6 @@ namespace {
   private:
     std::unique_ptr<PolyRing> mRing;
     Basis mIdeal;
-    std::unique_ptr<FreeModuleOrder> mOrder;
     PolyBasis mBasis;
     std::unique_ptr<F4MatrixBuilder> mBuilder;
   };

-- 
Alioth's /usr/local/bin/git-commit-notice on /srv/git.debian.org/git/debian-science/packages/mathicgb.git



More information about the debian-science-commits mailing list