From 4d72c20d9bf28d02bf2458eeb053ca27e001101a Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Patrick=20L=C3=BChne?= Date: Sun, 4 Sep 2016 23:30:08 +0200 Subject: [PATCH] Added separate simplification step to normalize in a single recursion. --- include/plasp/pddl/Expression.h | 4 ++- include/plasp/pddl/expressions/At.h | 3 ++- include/plasp/pddl/expressions/Binary.h | 20 ++++++++++++-- include/plasp/pddl/expressions/Imply.h | 2 +- include/plasp/pddl/expressions/NAry.h | 36 ++++++++++++++++++++++--- include/plasp/pddl/expressions/Not.h | 3 ++- src/plasp/pddl/Expression.cpp | 14 ++++++++++ src/plasp/pddl/expressions/At.cpp | 13 +++++++-- src/plasp/pddl/expressions/Imply.cpp | 8 +++--- src/plasp/pddl/expressions/Not.cpp | 13 ++++++++- tests/TestPDDLNormalization.cpp | 28 +++++++++++++++++++ 11 files changed, 128 insertions(+), 16 deletions(-) diff --git a/include/plasp/pddl/Expression.h b/include/plasp/pddl/Expression.h index 62d6a67..49079f1 100644 --- a/include/plasp/pddl/Expression.h +++ b/include/plasp/pddl/Expression.h @@ -109,7 +109,9 @@ class Expression virtual Type expressionType() const = 0; - virtual ExpressionPointer normalized(); + ExpressionPointer normalized(); + virtual ExpressionPointer simplified(); + virtual ExpressionPointer negationNormalized(); ExpressionPointer negated(); virtual void print(std::ostream &ostream) const = 0; diff --git a/include/plasp/pddl/expressions/At.h b/include/plasp/pddl/expressions/At.h index fdef30e..e76fc91 100644 --- a/include/plasp/pddl/expressions/At.h +++ b/include/plasp/pddl/expressions/At.h @@ -37,7 +37,8 @@ class At: public ExpressionCRTP void setArgument(ExpressionPointer argument); ExpressionPointer argument() const; - ExpressionPointer normalized() override; + ExpressionPointer simplified() override; + ExpressionPointer negationNormalized() override; void print(std::ostream &ostream) const override; diff --git a/include/plasp/pddl/expressions/Binary.h b/include/plasp/pddl/expressions/Binary.h index f300905..016b390 100644 --- a/include/plasp/pddl/expressions/Binary.h +++ b/include/plasp/pddl/expressions/Binary.h @@ -31,7 +31,8 @@ class Binary: public ExpressionCRTP void setArgument(size_t i, ExpressionPointer argument); const std::array &arguments() const; - ExpressionPointer normalized() override; + ExpressionPointer simplified() override; + ExpressionPointer negationNormalized() override; void print(std::ostream &ostream) const override; @@ -90,7 +91,22 @@ const std::array &Binary::arguments() const //////////////////////////////////////////////////////////////////////////////////////////////////// template -inline ExpressionPointer Binary::normalized() +inline ExpressionPointer Binary::simplified() +{ + for (size_t i = 0; i < m_arguments.size(); i++) + { + BOOST_ASSERT(m_arguments[i]); + + m_arguments[i] = m_arguments[i]->simplified(); + } + + return this; +} + +//////////////////////////////////////////////////////////////////////////////////////////////////// + +template +inline ExpressionPointer Binary::negationNormalized() { for (size_t i = 0; i < m_arguments.size(); i++) { diff --git a/include/plasp/pddl/expressions/Imply.h b/include/plasp/pddl/expressions/Imply.h index 8b1a6bf..61e4ebb 100644 --- a/include/plasp/pddl/expressions/Imply.h +++ b/include/plasp/pddl/expressions/Imply.h @@ -24,7 +24,7 @@ class Imply: public Binary static const std::string Identifier; public: - ExpressionPointer normalized() override; + ExpressionPointer simplified() override; }; //////////////////////////////////////////////////////////////////////////////////////////////////// diff --git a/include/plasp/pddl/expressions/NAry.h b/include/plasp/pddl/expressions/NAry.h index 62b1d6f..5d26d98 100644 --- a/include/plasp/pddl/expressions/NAry.h +++ b/include/plasp/pddl/expressions/NAry.h @@ -33,7 +33,8 @@ class NAry: public ExpressionCRTP Expressions &arguments(); const Expressions &arguments() const; - ExpressionPointer normalized() override; + ExpressionPointer simplified() override; + ExpressionPointer negationNormalized() override; void print(std::ostream &ostream) const override; @@ -120,13 +121,13 @@ Expressions &NAry::arguments() //////////////////////////////////////////////////////////////////////////////////////////////////// template -inline ExpressionPointer NAry::normalized() +inline ExpressionPointer NAry::simplified() { for (size_t i = 0; i < m_arguments.size(); i++) { BOOST_ASSERT(m_arguments[i]); - m_arguments[i] = m_arguments[i]->normalized(); + m_arguments[i] = m_arguments[i]->simplified(); } return this; @@ -134,6 +135,35 @@ inline ExpressionPointer NAry::normalized() //////////////////////////////////////////////////////////////////////////////////////////////////// +template +inline ExpressionPointer NAry::negationNormalized() +{ + for (size_t i = 0; i < m_arguments.size(); i++) + { + BOOST_ASSERT(m_arguments[i]); + + m_arguments[i] = m_arguments[i]->negationNormalized(); + } + + /*// Unify same-type children + for (size_t i = 0; i < m_arguments.size(); i++) + { + if (m_arguments[i]->expressionType() != Derived::ExpressionType) + continue; + + auto &nAryExpression = dynamic_cast(*m_arguments[i]); + + m_arguments.reserve(m_arguments.size() + nAryExpression.arguments().size()); + + m_arguments.emplace_back(nAryExpression.arguments()); + m_arguments.erase(const_iterator __position) + }*/ + + return this; +} + +//////////////////////////////////////////////////////////////////////////////////////////////////// + template inline void NAry::print(std::ostream &ostream) const { diff --git a/include/plasp/pddl/expressions/Not.h b/include/plasp/pddl/expressions/Not.h index 52ad743..23427c6 100644 --- a/include/plasp/pddl/expressions/Not.h +++ b/include/plasp/pddl/expressions/Not.h @@ -32,7 +32,8 @@ class Not: public ExpressionCRTP void setArgument(ExpressionPointer argument); ExpressionPointer argument() const; - ExpressionPointer normalized() override; + ExpressionPointer simplified() override; + ExpressionPointer negationNormalized() override; void print(std::ostream &ostream) const override; diff --git a/src/plasp/pddl/Expression.cpp b/src/plasp/pddl/Expression.cpp index 4f7df1c..ac69918 100644 --- a/src/plasp/pddl/Expression.cpp +++ b/src/plasp/pddl/Expression.cpp @@ -25,6 +25,20 @@ namespace pddl //////////////////////////////////////////////////////////////////////////////////////////////////// ExpressionPointer Expression::normalized() +{ + return simplified()->negationNormalized(); +} + +//////////////////////////////////////////////////////////////////////////////////////////////////// + +ExpressionPointer Expression::simplified() +{ + return this; +} + +//////////////////////////////////////////////////////////////////////////////////////////////////// + +ExpressionPointer Expression::negationNormalized() { return this; } diff --git a/src/plasp/pddl/expressions/At.cpp b/src/plasp/pddl/expressions/At.cpp index 2d0c245..e4ee339 100644 --- a/src/plasp/pddl/expressions/At.cpp +++ b/src/plasp/pddl/expressions/At.cpp @@ -1,5 +1,7 @@ #include +#include + namespace plasp { namespace pddl @@ -34,11 +36,18 @@ ExpressionPointer At::argument() const //////////////////////////////////////////////////////////////////////////////////////////////////// -ExpressionPointer At::normalized() +ExpressionPointer At::simplified() +{ + throw utils::TranslatorException("“at” predicates currently not supported"); +} + +//////////////////////////////////////////////////////////////////////////////////////////////////// + +ExpressionPointer At::negationNormalized() { BOOST_ASSERT(m_argument); - m_argument = m_argument->normalized(); + m_argument = m_argument->negationNormalized(); return this; } diff --git a/src/plasp/pddl/expressions/Imply.cpp b/src/plasp/pddl/expressions/Imply.cpp index e64f47f..9d2581e 100644 --- a/src/plasp/pddl/expressions/Imply.cpp +++ b/src/plasp/pddl/expressions/Imply.cpp @@ -21,13 +21,13 @@ const std::string Imply::Identifier = "imply"; //////////////////////////////////////////////////////////////////////////////////////////////////// -ExpressionPointer Imply::normalized() +ExpressionPointer Imply::simplified() { BOOST_ASSERT(m_arguments[0]); BOOST_ASSERT(m_arguments[1]); - m_arguments[0] = m_arguments[0]->normalized(); - m_arguments[1] = m_arguments[1]->normalized(); + m_arguments[0] = m_arguments[0]->simplified(); + m_arguments[1] = m_arguments[1]->simplified(); auto notArgument0 = NotPointer(new Not); notArgument0->setArgument(std::move(m_arguments[0])); @@ -36,7 +36,7 @@ ExpressionPointer Imply::normalized() orExpression->addArgument(std::move(notArgument0)); orExpression->addArgument(std::move(m_arguments[1])); - auto normalizedOrExpression = orExpression->normalized(); + auto normalizedOrExpression = orExpression->simplified(); if (normalizedOrExpression) return normalizedOrExpression; diff --git a/src/plasp/pddl/expressions/Not.cpp b/src/plasp/pddl/expressions/Not.cpp index b31382e..f71def7 100644 --- a/src/plasp/pddl/expressions/Not.cpp +++ b/src/plasp/pddl/expressions/Not.cpp @@ -37,7 +37,18 @@ ExpressionPointer Not::argument() const //////////////////////////////////////////////////////////////////////////////////////////////////// -ExpressionPointer Not::normalized() +ExpressionPointer Not::simplified() +{ + BOOST_ASSERT(m_argument); + + m_argument = m_argument->simplified(); + + return this; +} + +//////////////////////////////////////////////////////////////////////////////////////////////////// + +ExpressionPointer Not::negationNormalized() { BOOST_ASSERT(m_argument); diff --git a/tests/TestPDDLNormalization.cpp b/tests/TestPDDLNormalization.cpp index e65d831..bf01878 100644 --- a/tests/TestPDDLNormalization.cpp +++ b/tests/TestPDDLNormalization.cpp @@ -10,6 +10,34 @@ using namespace plasp::pddl; //////////////////////////////////////////////////////////////////////////////////////////////////// +TEST(PDDLNormalizationTests, Simplify) +{ + auto n1 = expressions::NotPointer(new expressions::Not); + auto n2 = expressions::NotPointer(new expressions::Not); + auto a = expressions::AndPointer(new expressions::And); + auto o = expressions::OrPointer(new expressions::Or); + auto i = expressions::ImplyPointer(new expressions::Imply); + + i->setArgument(0, new expressions::Dummy("a")); + i->setArgument(1, new expressions::Dummy("b")); + + o->addArgument(i); + o->addArgument(new expressions::Dummy("c")); + + a->addArgument(o); + a->addArgument(new expressions::Dummy("d")); + + n2->setArgument(a); + n1->setArgument(n2); + + std::stringstream output; + n1->simplified()->print(output); + + ASSERT_EQ(output.str(), "(not (not (and (or (or (not (a)) (b)) (c)) (d))))"); +} + +//////////////////////////////////////////////////////////////////////////////////////////////////// + TEST(PDDLNormalizationTests, Implication) { auto i = expressions::ImplyPointer(new expressions::Imply);