#ifndef __Ordering__
#define __Ordering__
#include <memory>
#include "Forwards.hpp"
#include "Debug/Assertion.hpp"
#include "Lib/Comparison.hpp"
#include "Lib/DArray.hpp"
#include "Kernel/Term.hpp"
#include "Kernel/SubstHelper.hpp"
namespace Kernel {
typedef std::unique_ptr<TermOrderingDiagram> TermOrderingDiagramUP;
namespace PredLevels {
constexpr static int MIN_USER_DEF = 1;
constexpr static int EQ = 0;
constexpr static int INEQ = 0;
};
using namespace Shell;
class Ordering
{
public:
enum [[nodiscard]] Result {
GREATER=1,
LESS=2,
EQUAL=3,
INCOMPARABLE=4
};
friend std::ostream& operator<<(std::ostream& out, Kernel::Ordering::Result const& r)
{
switch (r) {
case Kernel::Ordering::Result::GREATER: return out << "GREATER";
case Kernel::Ordering::Result::LESS: return out << "LESS";
case Kernel::Ordering::Result::EQUAL: return out << "EQUAL";
case Kernel::Ordering::Result::INCOMPARABLE: return out << "INCOMPARABLE";
}
ASSERTION_VIOLATION
return out << "UNKNOWN";
}
virtual ~Ordering() = default;
virtual Result compare(Literal* l1,Literal* l2) const = 0;
virtual Result compare(TermList t1,TermList t2) const = 0;
virtual Result compare(AppliedTerm lhs, AppliedTerm rhs) const
{ return compare(lhs.apply(), rhs.apply()); }
virtual Result compareUnidirectional(AppliedTerm t1, AppliedTerm t2) const
{ return compare(t1, t2); }
virtual TermOrderingDiagramUP createTermOrderingDiagram(bool ground = false) const;
virtual void show(std::ostream& out) const = 0;
static bool isGreaterOrEqual(Result r) { return (r == GREATER || r == EQUAL); }
void removeNonMaximal(LiteralList*& lits) const;
static Result fromComparison(Comparison c);
static Comparison intoComparison(Result c);
static Result reverse(Result r)
{
switch(r) {
case GREATER:
return LESS;
case LESS:
return GREATER;
case EQUAL:
case INCOMPARABLE:
return r;
default:
ASSERTION_VIOLATION;
}
}
static const char* resultToString(Result r);
static Ordering* create(Problem& prb, const Options& opt);
static bool trySetGlobalOrdering(OrderingSP ordering);
static bool unsetGlobalOrdering();
static Ordering* tryGetGlobalOrdering();
Result getEqualityArgumentOrder(Literal* eq) const;
protected:
Result compareEqualities(Literal* eq1, Literal* eq2) const;
private:
Result compare_s1Gt1(TermList s1,TermList s2,TermList t1,TermList t2) const;
Result compare_s1It1(TermList s1,TermList s2,TermList t1,TermList t2) const;
Result compare_s1It1_s2It2(TermList s1,TermList s2,TermList t1,TermList t2) const;
Result compare_s1Gt1_s2It2(TermList s1,TermList s2,TermList t1,TermList t2) const;
Result compare_s1Gt1_s2Lt2(TermList s1,TermList s2,TermList t1,TermList t2) const;
Result compare_s1Gt1_s1It2_s2It1(TermList s1,TermList s2,TermList t1,TermList t2) const;
static OrderingSP s_globalOrdering;
};
class PrecedenceOrdering
: public Ordering
{
public:
PrecedenceOrdering(PrecedenceOrdering&&) = default;
PrecedenceOrdering& operator=(PrecedenceOrdering&&) = default;
Result compare(Literal* l1, Literal* l2) const override;
void show(std::ostream&) const override;
virtual void showConcrete(std::ostream&) const = 0;
static DArray<int> testLevels();
#ifdef VDEBUG
bool usesQkboPrecedence() const { return _qkboPrecedence; }
#endif
static DArray<int> funcPrecFromOpts(Problem& prb, const Options& opt);
static DArray<int> predPrecFromOpts(Problem& prb, const Options& opt);
Result comparePredicatePrecedences(unsigned fun1, unsigned fun2) const;
int predicatePrecedence(unsigned pred) const;
protected:
virtual Result comparePredicates(Literal* l1,Literal* l2) const = 0;
PrecedenceOrdering(const DArray<int>& funcPrec, const DArray<int>& typeConPrec,
const DArray<int>& predPrec, const DArray<int>& predLevels,
bool reverseLCM, bool qkboPrecedence = false);
PrecedenceOrdering(Problem& prb, const Options& opt, const DArray<int>& predPrec, bool qkboPrecedence = false);
PrecedenceOrdering(Problem& prb, const Options& opt, bool qkboPrecedence = false);
static DArray<int> typeConPrecFromOpts(Problem& prb, const Options& opt);
static DArray<int> predLevelsFromOptsAndPrec(Problem& prb, const Options& opt, const DArray<int>& predicatePrecedences);
Result comparePrecedences(const Term* t1, const Term* t2) const;
Result compareFunctionPrecedences(unsigned fun1, unsigned fun2) const;
Result compareTypeConPrecedences(unsigned tyc1, unsigned tyc2) const;
int predicateLevel(unsigned pred) const;
unsigned _predicates;
unsigned _functions;
DArray<int> _predicateLevels;
DArray<int> _predicatePrecedences;
DArray<int> _functionPrecedences;
DArray<int> _typeConPrecedences;
static void checkLevelAssumptions(DArray<int> const&);
bool _reverseLCM;
bool _qkboPrecedence;
};
}
#endif