Parsing domains in two passes and continued working on parsing the initial state.
This commit is contained in:
parent
ff7a6b8c8f
commit
8428c20bd4
@ -26,7 +26,8 @@ class Domain
|
|||||||
Domain(Context &context);
|
Domain(Context &context);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
void readPDDL();
|
void findSections();
|
||||||
|
void parse();
|
||||||
|
|
||||||
void setName(std::string name);
|
void setName(std::string name);
|
||||||
const std::string &name() const;
|
const std::string &name() const;
|
||||||
@ -66,10 +67,20 @@ class Domain
|
|||||||
Context &m_context;
|
Context &m_context;
|
||||||
|
|
||||||
std::string m_name;
|
std::string m_name;
|
||||||
|
|
||||||
|
utils::Parser::Position m_requirementsPosition;
|
||||||
Requirements m_requirements;
|
Requirements m_requirements;
|
||||||
expressions::PrimitiveTypes m_primitiveTypes;
|
|
||||||
|
utils::Parser::Position m_typesPosition;
|
||||||
|
expressions::PrimitiveTypes m_types;
|
||||||
|
|
||||||
|
utils::Parser::Position m_constantsPosition;
|
||||||
expressions::Constants m_constants;
|
expressions::Constants m_constants;
|
||||||
expressions::PredicateDeclarations m_predicateDeclarations;
|
|
||||||
|
utils::Parser::Position m_predicatesPosition;
|
||||||
|
expressions::PredicateDeclarations m_predicates;
|
||||||
|
|
||||||
|
std::vector<utils::Parser::Position> m_actionPositions;
|
||||||
std::vector<std::unique_ptr<Action>> m_actions;
|
std::vector<std::unique_ptr<Action>> m_actions;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
@ -7,20 +7,27 @@ namespace plasp
|
|||||||
{
|
{
|
||||||
namespace pddl
|
namespace pddl
|
||||||
{
|
{
|
||||||
namespace expressions
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// InitialState
|
||||||
|
//
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
class InitialState
|
||||||
{
|
{
|
||||||
|
public:
|
||||||
|
static std::unique_ptr<InitialState> parseDeclaration(Context &context, const Problem &problem);
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
public:
|
||||||
//
|
const Expressions &facts() const;
|
||||||
// Type
|
|
||||||
//
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
ExpressionPointer parseInitialState(Context &context);
|
private:
|
||||||
|
Expressions m_facts;
|
||||||
|
};
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
@ -3,6 +3,7 @@
|
|||||||
|
|
||||||
#include <plasp/pddl/Context.h>
|
#include <plasp/pddl/Context.h>
|
||||||
#include <plasp/pddl/Expression.h>
|
#include <plasp/pddl/Expression.h>
|
||||||
|
#include <plasp/pddl/InitialState.h>
|
||||||
#include <plasp/pddl/Requirement.h>
|
#include <plasp/pddl/Requirement.h>
|
||||||
|
|
||||||
namespace plasp
|
namespace plasp
|
||||||
@ -21,7 +22,7 @@ class Problem
|
|||||||
public:
|
public:
|
||||||
Problem(Context &context, Domain &domain);
|
Problem(Context &context, Domain &domain);
|
||||||
|
|
||||||
void readPDDL();
|
void parse();
|
||||||
|
|
||||||
bool isDeclared() const;
|
bool isDeclared() const;
|
||||||
|
|
||||||
@ -37,6 +38,9 @@ class Problem
|
|||||||
expressions::Constants &objects();
|
expressions::Constants &objects();
|
||||||
const expressions::Constants &objects() const;
|
const expressions::Constants &objects() const;
|
||||||
|
|
||||||
|
InitialState &initialState();
|
||||||
|
const InitialState &initialState() const;
|
||||||
|
|
||||||
void checkConsistency();
|
void checkConsistency();
|
||||||
|
|
||||||
private:
|
private:
|
||||||
@ -49,6 +53,8 @@ class Problem
|
|||||||
|
|
||||||
void parseObjectSection();
|
void parseObjectSection();
|
||||||
|
|
||||||
|
void parseInitialStateSection();
|
||||||
|
|
||||||
Context &m_context;
|
Context &m_context;
|
||||||
Domain &m_domain;
|
Domain &m_domain;
|
||||||
bool m_isDeclared;
|
bool m_isDeclared;
|
||||||
@ -57,6 +63,8 @@ class Problem
|
|||||||
Requirements m_requirements;
|
Requirements m_requirements;
|
||||||
|
|
||||||
expressions::Constants m_objects;
|
expressions::Constants m_objects;
|
||||||
|
|
||||||
|
std::unique_ptr<InitialState> m_initialState;
|
||||||
};
|
};
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
@ -27,7 +27,8 @@ class Constant: public Expression
|
|||||||
static void parseTypedDeclaration(Context &context, Problem &problem);
|
static void parseTypedDeclaration(Context &context, Problem &problem);
|
||||||
static void parseTypedDeclarations(Context &context, Problem &problem);
|
static void parseTypedDeclarations(Context &context, Problem &problem);
|
||||||
|
|
||||||
static Constant *parseAndFind(Context &context, const ExpressionContext &expressionContext);
|
static Constant *parseAndFind(Context &context, const Domain &domain);
|
||||||
|
static Constant *parseAndFind(Context &context, const Problem &problem);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
void accept(ExpressionVisitor &expressionVisitor) const override;
|
void accept(ExpressionVisitor &expressionVisitor) const override;
|
||||||
|
@ -21,6 +21,7 @@ class Predicate: public Expression
|
|||||||
public:
|
public:
|
||||||
static PredicatePointer parse(std::string name, Context &context,
|
static PredicatePointer parse(std::string name, Context &context,
|
||||||
ExpressionContext &expressionContext);
|
ExpressionContext &expressionContext);
|
||||||
|
static PredicatePointer parse(std::string name, Context &context, const Problem &problem);
|
||||||
|
|
||||||
public:
|
public:
|
||||||
void accept(ExpressionVisitor &expressionVisitor) const override;
|
void accept(ExpressionVisitor &expressionVisitor) const override;
|
||||||
|
@ -106,12 +106,12 @@ void Description::parseContent()
|
|||||||
throw ConsistencyException("No PDDL domain specified");
|
throw ConsistencyException("No PDDL domain specified");
|
||||||
|
|
||||||
m_context.parser.seek(m_domainPosition);
|
m_context.parser.seek(m_domainPosition);
|
||||||
m_domain->readPDDL();
|
m_domain->parse();
|
||||||
|
|
||||||
if (m_problemPosition != -1)
|
if (m_problemPosition != -1)
|
||||||
{
|
{
|
||||||
m_context.parser.seek(m_problemPosition);
|
m_context.parser.seek(m_problemPosition);
|
||||||
m_problem->readPDDL();
|
m_problem->parse();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -119,41 +119,45 @@ void Description::parseContent()
|
|||||||
|
|
||||||
void Description::findSections()
|
void Description::findSections()
|
||||||
{
|
{
|
||||||
while (true)
|
auto &parser = m_context.parser;
|
||||||
|
|
||||||
|
parser.skipWhiteSpace();
|
||||||
|
|
||||||
|
while (!parser.atEndOfStream())
|
||||||
{
|
{
|
||||||
m_context.parser.skipWhiteSpace();
|
const auto position = parser.position();
|
||||||
|
|
||||||
if (m_context.parser.atEndOfStream())
|
parser.expect<std::string>("(");
|
||||||
return;
|
parser.expect<std::string>("define");
|
||||||
|
parser.expect<std::string>("(");
|
||||||
|
|
||||||
const auto position = m_context.parser.position();
|
if (parser.probe<std::string>("domain"))
|
||||||
|
|
||||||
m_context.parser.expect<std::string>("(");
|
|
||||||
m_context.parser.expect<std::string>("define");
|
|
||||||
m_context.parser.expect<std::string>("(");
|
|
||||||
|
|
||||||
if (m_context.parser.probe<std::string>("domain"))
|
|
||||||
{
|
{
|
||||||
if (m_domainPosition != -1)
|
if (m_domainPosition != -1)
|
||||||
throw utils::ParserException(m_context.parser, "PDDL description may not contain two domains");
|
throw utils::ParserException(parser, "PDDL description may not contain two domains");
|
||||||
|
|
||||||
m_domainPosition = position;
|
m_domainPosition = position;
|
||||||
|
|
||||||
|
parser.seek(position);
|
||||||
|
m_domain->findSections();
|
||||||
}
|
}
|
||||||
else if (m_context.parser.probe<std::string>("problem"))
|
else if (m_context.parser.probe<std::string>("problem"))
|
||||||
{
|
{
|
||||||
if (m_problemPosition != -1)
|
if (m_problemPosition != -1)
|
||||||
throw utils::ParserException(m_context.parser, "PDDL description may currently not contain two problems");
|
throw utils::ParserException(parser, "PDDL description may currently not contain two problems");
|
||||||
|
|
||||||
m_problemPosition = position;
|
m_problemPosition = position;
|
||||||
|
|
||||||
|
skipSection(parser);
|
||||||
|
skipSection(parser);
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
const auto sectionIdentifier = m_context.parser.parse<std::string>();
|
const auto sectionIdentifier = parser.parse<std::string>();
|
||||||
throw utils::ParserException(m_context.parser, "Unknown PDDL section \"" + sectionIdentifier + "\"");
|
throw utils::ParserException(parser, "Unknown PDDL section \"" + sectionIdentifier + "\"");
|
||||||
}
|
}
|
||||||
|
|
||||||
skipSection(m_context.parser);
|
m_context.parser.skipWhiteSpace();
|
||||||
skipSection(m_context.parser);
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -11,6 +11,7 @@
|
|||||||
#include <plasp/pddl/expressions/Variable.h>
|
#include <plasp/pddl/expressions/Variable.h>
|
||||||
#include <plasp/utils/IO.h>
|
#include <plasp/utils/IO.h>
|
||||||
#include <plasp/utils/ParserException.h>
|
#include <plasp/utils/ParserException.h>
|
||||||
|
#include <plasp/utils/ParserWarning.h>
|
||||||
|
|
||||||
namespace plasp
|
namespace plasp
|
||||||
{
|
{
|
||||||
@ -24,35 +25,129 @@ namespace pddl
|
|||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
Domain::Domain(Context &context)
|
Domain::Domain(Context &context)
|
||||||
: m_context(context)
|
: m_context(context),
|
||||||
|
m_requirementsPosition{-1},
|
||||||
|
m_typesPosition{-1},
|
||||||
|
m_constantsPosition{-1},
|
||||||
|
m_predicatesPosition{-1}
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
void Domain::readPDDL()
|
void Domain::findSections()
|
||||||
{
|
{
|
||||||
m_context.parser.expect<std::string>("(");
|
auto &parser = m_context.parser;
|
||||||
m_context.parser.expect<std::string>("define");
|
|
||||||
m_context.parser.expect<std::string>("(");
|
parser.expect<std::string>("(");
|
||||||
m_context.parser.expect<std::string>("domain");
|
parser.expect<std::string>("define");
|
||||||
|
parser.expect<std::string>("(");
|
||||||
|
parser.expect<std::string>("domain");
|
||||||
|
|
||||||
m_name = m_context.parser.parseIdentifier(isIdentifier);
|
m_name = m_context.parser.parseIdentifier(isIdentifier);
|
||||||
|
|
||||||
|
std::cout << "Found domain " << m_name << std::endl;
|
||||||
|
|
||||||
|
parser.expect<std::string>(")");
|
||||||
|
|
||||||
|
const auto setSectionPosition =
|
||||||
|
[&](const std::string §ionName, auto §ionPosition, const auto value, bool unique = false)
|
||||||
|
{
|
||||||
|
if (unique && sectionPosition != -1)
|
||||||
|
throw utils::ParserException(parser, "Only one \":" + sectionName + "\" section allowed");
|
||||||
|
|
||||||
|
sectionPosition = value;
|
||||||
|
};
|
||||||
|
|
||||||
|
parser.skipWhiteSpace();
|
||||||
|
|
||||||
|
// Find sections
|
||||||
|
while (parser.currentCharacter() != ')')
|
||||||
|
{
|
||||||
|
const auto position = parser.position();
|
||||||
|
|
||||||
|
parser.expect<std::string>("(");
|
||||||
|
parser.expect<std::string>(":");
|
||||||
|
|
||||||
|
// Save the parser position of the individual sections for later parsing
|
||||||
|
if (parser.probe<std::string>("requirements"))
|
||||||
|
setSectionPosition("requirements", m_requirementsPosition, position, true);
|
||||||
|
else if (parser.probe<std::string>("types"))
|
||||||
|
setSectionPosition("types", m_typesPosition, position, true);
|
||||||
|
else if (parser.probe<std::string>("constants"))
|
||||||
|
setSectionPosition("constants", m_constantsPosition, position, true);
|
||||||
|
else if (parser.probe<std::string>("predicates"))
|
||||||
|
setSectionPosition("predicates", m_predicatesPosition, position, true);
|
||||||
|
else if (parser.probe<std::string>("action"))
|
||||||
|
{
|
||||||
|
m_actionPositions.emplace_back(-1);
|
||||||
|
setSectionPosition("action", m_actionPositions.back(), position);
|
||||||
|
}
|
||||||
|
else if (parser.probe<std::string>("functions")
|
||||||
|
|| parser.probe<std::string>("constraints")
|
||||||
|
|| parser.probe<std::string>("durative-action")
|
||||||
|
|| parser.probe<std::string>("derived"))
|
||||||
|
{
|
||||||
|
parser.seek(position);
|
||||||
|
m_context.logger.parserWarning(parser, "Section type currently unsupported");
|
||||||
|
parser.advance();
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
const auto sectionIdentifier = parser.parseIdentifier(isIdentifier);
|
||||||
|
|
||||||
|
parser.seek(position);
|
||||||
|
throw utils::ParserException(m_context.parser, "Unknown domain section \"" + sectionIdentifier + "\"");
|
||||||
|
}
|
||||||
|
|
||||||
|
// Skip section for now and parse it later
|
||||||
|
skipSection(parser);
|
||||||
|
|
||||||
|
parser.skipWhiteSpace();
|
||||||
|
}
|
||||||
|
|
||||||
|
parser.expect<std::string>(")");
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
void Domain::parse()
|
||||||
|
{
|
||||||
|
auto &parser = m_context.parser;
|
||||||
|
|
||||||
std::cout << "Parsing domain " << m_name << std::endl;
|
std::cout << "Parsing domain " << m_name << std::endl;
|
||||||
|
|
||||||
m_context.parser.expect<std::string>(")");
|
if (m_requirementsPosition != -1)
|
||||||
|
|
||||||
while (true)
|
|
||||||
{
|
{
|
||||||
m_context.parser.skipWhiteSpace();
|
parser.seek(m_requirementsPosition);
|
||||||
|
parseRequirementSection();
|
||||||
if (m_context.parser.probe(')'))
|
|
||||||
break;
|
|
||||||
|
|
||||||
parseSection();
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (m_typesPosition != -1)
|
||||||
|
{
|
||||||
|
parser.seek(m_typesPosition);
|
||||||
|
parseTypeSection();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (m_constantsPosition != -1)
|
||||||
|
{
|
||||||
|
parser.seek(m_constantsPosition);
|
||||||
|
parseConstantSection();
|
||||||
|
}
|
||||||
|
|
||||||
|
if (m_predicatesPosition != -1)
|
||||||
|
{
|
||||||
|
parser.seek(m_predicatesPosition);
|
||||||
|
parsePredicateSection();
|
||||||
|
}
|
||||||
|
|
||||||
|
for (size_t i = 0; i < m_actionPositions.size(); i++)
|
||||||
|
if (m_actionPositions[i] != -1)
|
||||||
|
{
|
||||||
|
parser.seek(m_actionPositions[i]);
|
||||||
|
parseActionSection();
|
||||||
|
}
|
||||||
|
|
||||||
computeDerivedRequirements();
|
computeDerivedRequirements();
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -81,14 +176,14 @@ const Requirements &Domain::requirements() const
|
|||||||
|
|
||||||
expressions::PrimitiveTypes &Domain::types()
|
expressions::PrimitiveTypes &Domain::types()
|
||||||
{
|
{
|
||||||
return m_primitiveTypes;
|
return m_types;
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
const expressions::PrimitiveTypes &Domain::types() const
|
const expressions::PrimitiveTypes &Domain::types() const
|
||||||
{
|
{
|
||||||
return m_primitiveTypes;
|
return m_types;
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
@ -109,14 +204,14 @@ const expressions::Constants &Domain::constants() const
|
|||||||
|
|
||||||
expressions::PredicateDeclarations &Domain::predicates()
|
expressions::PredicateDeclarations &Domain::predicates()
|
||||||
{
|
{
|
||||||
return m_predicateDeclarations;
|
return m_predicates;
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
const expressions::PredicateDeclarations &Domain::predicates() const
|
const expressions::PredicateDeclarations &Domain::predicates() const
|
||||||
{
|
{
|
||||||
return m_predicateDeclarations;
|
return m_predicates;
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
@ -135,52 +230,21 @@ const std::vector<std::unique_ptr<Action>> &Domain::actions() const
|
|||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
void Domain::parseSection()
|
void Domain::parseRequirementSection()
|
||||||
{
|
{
|
||||||
auto &parser = m_context.parser;
|
auto &parser = m_context.parser;
|
||||||
|
|
||||||
parser.expect<std::string>("(");
|
parser.expect<std::string>("(");
|
||||||
parser.expect<std::string>(":");
|
parser.expect<std::string>(":");
|
||||||
|
parser.expect<std::string>("requirements");
|
||||||
|
|
||||||
// TODO: check order of the sections
|
while (parser.currentCharacter() != ')')
|
||||||
if (parser.probe<std::string>("requirements"))
|
|
||||||
parseRequirementSection();
|
|
||||||
else if (parser.probe<std::string>("types"))
|
|
||||||
parseTypeSection();
|
|
||||||
else if (parser.probe<std::string>("constants"))
|
|
||||||
parseConstantSection();
|
|
||||||
else if (parser.probe<std::string>("predicates"))
|
|
||||||
parsePredicateSection();
|
|
||||||
else if (parser.probe<std::string>("action"))
|
|
||||||
parseActionSection();
|
|
||||||
else if (parser.probe<std::string>("functions")
|
|
||||||
|| parser.probe<std::string>("constraints")
|
|
||||||
|| parser.probe<std::string>("durative-action")
|
|
||||||
|| parser.probe<std::string>("derived"))
|
|
||||||
{
|
{
|
||||||
std::cout << "Skipping section" << std::endl;
|
parser.expect<std::string>(":");
|
||||||
skipSection(m_context.parser);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
const auto sectionIdentifier = parser.parseIdentifier(isIdentifier);
|
|
||||||
throw utils::ParserException(m_context.parser, "Unknown domain section \"" + sectionIdentifier + "\"");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void Domain::parseRequirementSection()
|
|
||||||
{
|
|
||||||
m_context.parser.skipWhiteSpace();
|
|
||||||
|
|
||||||
while (m_context.parser.currentCharacter() != ')')
|
|
||||||
{
|
|
||||||
m_context.parser.expect<std::string>(":");
|
|
||||||
|
|
||||||
m_requirements.emplace_back(Requirement::parse(m_context));
|
m_requirements.emplace_back(Requirement::parse(m_context));
|
||||||
|
|
||||||
m_context.parser.skipWhiteSpace();
|
parser.skipWhiteSpace();
|
||||||
}
|
}
|
||||||
|
|
||||||
// TODO: do this check only once the problem is parsed
|
// TODO: do this check only once the problem is parsed
|
||||||
@ -188,7 +252,7 @@ void Domain::parseRequirementSection()
|
|||||||
if (m_requirements.empty())
|
if (m_requirements.empty())
|
||||||
m_requirements.emplace_back(Requirement::Type::STRIPS);
|
m_requirements.emplace_back(Requirement::Type::STRIPS);
|
||||||
|
|
||||||
m_context.parser.expect<std::string>(")");
|
parser.expect<std::string>(")");
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
@ -258,60 +322,82 @@ void Domain::computeDerivedRequirements()
|
|||||||
|
|
||||||
void Domain::parseTypeSection()
|
void Domain::parseTypeSection()
|
||||||
{
|
{
|
||||||
|
auto &parser = m_context.parser;
|
||||||
|
|
||||||
|
parser.expect<std::string>("(");
|
||||||
|
parser.expect<std::string>(":");
|
||||||
|
parser.expect<std::string>("types");
|
||||||
|
|
||||||
checkRequirement(Requirement::Type::Typing);
|
checkRequirement(Requirement::Type::Typing);
|
||||||
|
|
||||||
m_context.parser.skipWhiteSpace();
|
parser.skipWhiteSpace();
|
||||||
|
|
||||||
// Store types and their parent types
|
// Store types and their parent types
|
||||||
while (!m_context.parser.probe(')'))
|
while (parser.currentCharacter() != ')')
|
||||||
{
|
{
|
||||||
if (m_context.parser.currentCharacter() == '(')
|
if (parser.currentCharacter() == '(')
|
||||||
throw utils::ParserException(m_context.parser, "Only primitive types are allowed in type section");
|
throw utils::ParserException(parser, "Only primitive types are allowed in type section");
|
||||||
|
|
||||||
expressions::PrimitiveType::parseTypedDeclaration(m_context, *this);
|
expressions::PrimitiveType::parseTypedDeclaration(m_context, *this);
|
||||||
|
|
||||||
m_context.parser.skipWhiteSpace();
|
parser.skipWhiteSpace();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
parser.expect<std::string>(")");
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
void Domain::parseConstantSection()
|
void Domain::parseConstantSection()
|
||||||
{
|
{
|
||||||
m_context.parser.skipWhiteSpace();
|
auto &parser = m_context.parser;
|
||||||
|
|
||||||
|
parser.expect<std::string>("(");
|
||||||
|
parser.expect<std::string>(":");
|
||||||
|
parser.expect<std::string>("constants");
|
||||||
|
|
||||||
// Store constants
|
// Store constants
|
||||||
expressions::Constant::parseTypedDeclarations(m_context, *this);
|
expressions::Constant::parseTypedDeclarations(m_context, *this);
|
||||||
|
|
||||||
m_context.parser.expect<std::string>(")");
|
parser.expect<std::string>(")");
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
void Domain::parsePredicateSection()
|
void Domain::parsePredicateSection()
|
||||||
{
|
{
|
||||||
m_context.parser.skipWhiteSpace();
|
auto &parser = m_context.parser;
|
||||||
|
|
||||||
|
parser.expect<std::string>("(");
|
||||||
|
parser.expect<std::string>(":");
|
||||||
|
parser.expect<std::string>("predicates");
|
||||||
|
|
||||||
|
parser.skipWhiteSpace();
|
||||||
|
|
||||||
// Store predicates and their arguments
|
// Store predicates and their arguments
|
||||||
while (m_context.parser.currentCharacter() != ')')
|
while (parser.currentCharacter() != ')')
|
||||||
{
|
{
|
||||||
expressions::PredicateDeclaration::parse(m_context, *this);
|
expressions::PredicateDeclaration::parse(m_context, *this);
|
||||||
|
|
||||||
m_context.parser.skipWhiteSpace();
|
parser.skipWhiteSpace();
|
||||||
}
|
}
|
||||||
|
|
||||||
m_context.parser.expect<std::string>(")");
|
parser.expect<std::string>(")");
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
void Domain::parseActionSection()
|
void Domain::parseActionSection()
|
||||||
{
|
{
|
||||||
m_context.parser.skipWhiteSpace();
|
auto &parser = m_context.parser;
|
||||||
|
|
||||||
|
parser.expect<std::string>("(");
|
||||||
|
parser.expect<std::string>(":");
|
||||||
|
parser.expect<std::string>("action");
|
||||||
|
|
||||||
Action::parseDeclaration(m_context, *this);
|
Action::parseDeclaration(m_context, *this);
|
||||||
|
|
||||||
m_context.parser.expect<std::string>(")");
|
parser.expect<std::string>(")");
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
@ -4,6 +4,7 @@
|
|||||||
#include <plasp/pddl/Domain.h>
|
#include <plasp/pddl/Domain.h>
|
||||||
#include <plasp/pddl/ExpressionContext.h>
|
#include <plasp/pddl/ExpressionContext.h>
|
||||||
#include <plasp/pddl/Identifier.h>
|
#include <plasp/pddl/Identifier.h>
|
||||||
|
#include <plasp/pddl/IO.h>
|
||||||
#include <plasp/pddl/expressions/And.h>
|
#include <plasp/pddl/expressions/And.h>
|
||||||
#include <plasp/pddl/expressions/Imply.h>
|
#include <plasp/pddl/expressions/Imply.h>
|
||||||
#include <plasp/pddl/expressions/Not.h>
|
#include <plasp/pddl/expressions/Not.h>
|
||||||
@ -33,10 +34,10 @@ ExpressionPointer parsePredicate(Context &context, ExpressionContext &expression
|
|||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
[[noreturn]] void throwUnsupported(const utils::Parser &parser,
|
inline void warnUnsupported(Context &context, const std::string &expressionIdentifier)
|
||||||
const std::string &expressionIdentifier)
|
|
||||||
{
|
{
|
||||||
throw utils::ParserException(parser, "Expression type \"" + expressionIdentifier + "\" currently unsupported in this context");
|
context.logger.parserWarning(context.parser, "Expression type \"" + expressionIdentifier + "\" currently unsupported in this context");
|
||||||
|
skipSection(context.parser);
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
@ -58,7 +59,9 @@ ExpressionPointer parsePreconditionExpression(Context &context,
|
|||||||
else if (expressionIdentifier == "forall"
|
else if (expressionIdentifier == "forall"
|
||||||
|| expressionIdentifier == "preference")
|
|| expressionIdentifier == "preference")
|
||||||
{
|
{
|
||||||
throwUnsupported(context.parser, expressionIdentifier);
|
warnUnsupported(context, expressionIdentifier);
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
expression = parseExpressionContent(expressionIdentifier, context, expressionContext);
|
expression = parseExpressionContent(expressionIdentifier, context, expressionContext);
|
||||||
@ -116,7 +119,9 @@ ExpressionPointer parseExpressionContent(const std::string &expressionIdentifier
|
|||||||
|| expressionIdentifier == ">="
|
|| expressionIdentifier == ">="
|
||||||
|| expressionIdentifier == "<=")
|
|| expressionIdentifier == "<=")
|
||||||
{
|
{
|
||||||
throwUnsupported(context.parser, expressionIdentifier);
|
warnUnsupported(context, expressionIdentifier);
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
auto &predicateDeclarations = expressionContext.domain.predicates();
|
auto &predicateDeclarations = expressionContext.domain.predicates();
|
||||||
@ -132,7 +137,7 @@ ExpressionPointer parseExpressionContent(const std::string &expressionIdentifier
|
|||||||
if (match != predicateDeclarations.cend())
|
if (match != predicateDeclarations.cend())
|
||||||
return expressions::Predicate::parse(expressionIdentifier, context, expressionContext);
|
return expressions::Predicate::parse(expressionIdentifier, context, expressionContext);
|
||||||
|
|
||||||
throw utils::ParserException(context.parser, "Expression \"" + expressionIdentifier + "\" not allowed in this context");
|
throw utils::ParserException(context.parser, "Unknown expression \"" + expressionIdentifier + "\"");
|
||||||
}
|
}
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
@ -150,7 +155,9 @@ ExpressionPointer parseEffectExpression(Context &context, ExpressionContext &exp
|
|||||||
else if (expressionIdentifier == "forall"
|
else if (expressionIdentifier == "forall"
|
||||||
|| expressionIdentifier == "when")
|
|| expressionIdentifier == "when")
|
||||||
{
|
{
|
||||||
throwUnsupported(context.parser, expressionIdentifier);
|
warnUnsupported(context, expressionIdentifier);
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
expression = parseEffectBodyExpressionContent(expressionIdentifier, context, expressionContext);
|
expression = parseEffectBodyExpressionContent(expressionIdentifier, context, expressionContext);
|
||||||
@ -177,7 +184,9 @@ ExpressionPointer parseEffectBodyExpressionContent(const std::string &expression
|
|||||||
|| expressionIdentifier == "increase"
|
|| expressionIdentifier == "increase"
|
||||||
|| expressionIdentifier == "decrease")
|
|| expressionIdentifier == "decrease")
|
||||||
{
|
{
|
||||||
throwUnsupported(context.parser, expressionIdentifier);
|
warnUnsupported(context, expressionIdentifier);
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto &predicateDeclarations = expressionContext.domain.predicates();
|
const auto &predicateDeclarations = expressionContext.domain.predicates();
|
||||||
|
63
src/plasp/pddl/InitialState.cpp
Normal file
63
src/plasp/pddl/InitialState.cpp
Normal file
@ -0,0 +1,63 @@
|
|||||||
|
#include <plasp/pddl/InitialState.h>
|
||||||
|
|
||||||
|
#include <plasp/pddl/Context.h>
|
||||||
|
#include <plasp/pddl/Identifier.h>
|
||||||
|
#include <plasp/pddl/IO.h>
|
||||||
|
#include <plasp/pddl/expressions/Predicate.h>
|
||||||
|
#include <plasp/utils/ParserException.h>
|
||||||
|
|
||||||
|
namespace plasp
|
||||||
|
{
|
||||||
|
namespace pddl
|
||||||
|
{
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
//
|
||||||
|
// InitialState
|
||||||
|
//
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
inline void warnUnsupported(Context &context, const std::string &expressionIdentifier)
|
||||||
|
{
|
||||||
|
context.logger.parserWarning(context.parser, "Expression type \"" + expressionIdentifier + "\" currently unsupported in this context");
|
||||||
|
skipSection(context.parser);
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
std::unique_ptr<InitialState> InitialState::parseDeclaration(Context &context, const Problem &problem)
|
||||||
|
{
|
||||||
|
auto initialState = std::make_unique<InitialState>(InitialState());
|
||||||
|
|
||||||
|
while (context.parser.currentCharacter() != ')')
|
||||||
|
{
|
||||||
|
context.parser.expect<std::string>("(");
|
||||||
|
|
||||||
|
ExpressionPointer expression;
|
||||||
|
|
||||||
|
const auto expressionIdentifier = context.parser.parseIdentifier(isIdentifier);
|
||||||
|
|
||||||
|
if (expressionIdentifier == "at"
|
||||||
|
|| expressionIdentifier == "="
|
||||||
|
|| expressionIdentifier == "not")
|
||||||
|
{
|
||||||
|
warnUnsupported(context, expressionIdentifier);
|
||||||
|
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
|
||||||
|
// If none of the above types apply, the content is a predicate over constants and objects
|
||||||
|
initialState->m_facts.emplace_back(expressions::Predicate::parse(expressionIdentifier, context, problem));
|
||||||
|
|
||||||
|
context.parser.expect<std::string>(")");
|
||||||
|
|
||||||
|
context.parser.skipWhiteSpace();
|
||||||
|
}
|
||||||
|
|
||||||
|
return initialState;
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
}
|
||||||
|
}
|
@ -29,7 +29,7 @@ Problem::Problem(Context &context, Domain &domain)
|
|||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
void Problem::readPDDL()
|
void Problem::parse()
|
||||||
{
|
{
|
||||||
m_context.parser.expect<std::string>("(");
|
m_context.parser.expect<std::string>("(");
|
||||||
m_context.parser.expect<std::string>("define");
|
m_context.parser.expect<std::string>("define");
|
||||||
@ -122,8 +122,9 @@ void Problem::parseSection()
|
|||||||
parseRequirementSection();
|
parseRequirementSection();
|
||||||
else if (parser.probe<std::string>("objects"))
|
else if (parser.probe<std::string>("objects"))
|
||||||
parseObjectSection();
|
parseObjectSection();
|
||||||
else if (parser.probe<std::string>("init")
|
else if (parser.probe<std::string>("init"))
|
||||||
|| parser.probe<std::string>("goal")
|
parseInitialStateSection();
|
||||||
|
else if (parser.probe<std::string>("goal")
|
||||||
|| parser.probe<std::string>("constraints")
|
|| parser.probe<std::string>("constraints")
|
||||||
|| parser.probe<std::string>("metric")
|
|| parser.probe<std::string>("metric")
|
||||||
|| parser.probe<std::string>("length"))
|
|| parser.probe<std::string>("length"))
|
||||||
@ -255,6 +256,33 @@ void Problem::parseObjectSection()
|
|||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
void Problem::parseInitialStateSection()
|
||||||
|
{
|
||||||
|
m_initialState = InitialState::parseDeclaration(m_context, *this);
|
||||||
|
|
||||||
|
m_context.parser.expect<std::string>(")");
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
InitialState &Problem::initialState()
|
||||||
|
{
|
||||||
|
BOOST_ASSERT(m_initialState);
|
||||||
|
|
||||||
|
return *m_initialState;
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
const InitialState &Problem::initialState() const
|
||||||
|
{
|
||||||
|
BOOST_ASSERT(m_initialState);
|
||||||
|
|
||||||
|
return *m_initialState;
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
void Problem::checkConsistency()
|
void Problem::checkConsistency()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
@ -134,24 +134,37 @@ void Constant::parseTypedDeclarations(Context &context, Problem &problem)
|
|||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
Constant *Constant::parseAndFind(Context &context, const ExpressionContext &expressionContext)
|
Constant *Constant::parseAndFind(Context &context, const Domain &domain)
|
||||||
{
|
{
|
||||||
context.parser.skipWhiteSpace();
|
context.parser.skipWhiteSpace();
|
||||||
|
|
||||||
const auto constantName = context.parser.parseIdentifier(isIdentifier);
|
const auto constantName = context.parser.parseIdentifier(isIdentifier);
|
||||||
|
|
||||||
auto *constant = parseAndFind(constantName, expressionContext.domain.constants());
|
auto *constant = parseAndFind(constantName, domain.constants());
|
||||||
|
|
||||||
|
if (constant != nullptr)
|
||||||
|
return constant;
|
||||||
|
|
||||||
|
throw utils::ParserException(context.parser, "Constant \"" + constantName + "\" used but never declared");
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
Constant *Constant::parseAndFind(Context &context, const Problem &problem)
|
||||||
|
{
|
||||||
|
context.parser.skipWhiteSpace();
|
||||||
|
|
||||||
|
const auto constantName = context.parser.parseIdentifier(isIdentifier);
|
||||||
|
|
||||||
|
auto *constant = parseAndFind(constantName, problem.domain().constants());
|
||||||
|
|
||||||
if (constant)
|
if (constant)
|
||||||
return constant;
|
return constant;
|
||||||
|
|
||||||
if (expressionContext.problem)
|
constant = parseAndFind(constantName, problem.objects());
|
||||||
{
|
|
||||||
constant = parseAndFind(constantName, expressionContext.problem->objects());
|
|
||||||
|
|
||||||
if (constant)
|
if (constant)
|
||||||
return constant;
|
return constant;
|
||||||
}
|
|
||||||
|
|
||||||
throw utils::ParserException(context.parser, "Constant \"" + constantName + "\" used but never declared");
|
throw utils::ParserException(context.parser, "Constant \"" + constantName + "\" used but never declared");
|
||||||
}
|
}
|
||||||
|
@ -1,54 +0,0 @@
|
|||||||
#include <plasp/pddl/expressions/Type.h>
|
|
||||||
|
|
||||||
#include <plasp/pddl/Context.h>
|
|
||||||
#include <plasp/pddl/Identifier.h>
|
|
||||||
#include <plasp/pddl/expressions/Predicate.h>
|
|
||||||
#include <plasp/utils/IO.h>
|
|
||||||
#include <plasp/utils/ParserException.h>
|
|
||||||
|
|
||||||
namespace plasp
|
|
||||||
{
|
|
||||||
namespace pddl
|
|
||||||
{
|
|
||||||
namespace expressions
|
|
||||||
{
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
||||||
//
|
|
||||||
// InitialState
|
|
||||||
//
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
void throwUnsupported(const utils::Parser &parser, const std::string &expressionIdentifier)
|
|
||||||
{
|
|
||||||
throw utils::ParserException(parser, "Expression type \"" + expressionIdentifier + "\" currently unsupported in this context");
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
ExpressionPointer parseInitialState(Context &context)
|
|
||||||
{
|
|
||||||
context.parser.expect<std::string>("(");
|
|
||||||
|
|
||||||
const auto expressionIdentifier = context.parser.parseIdentifier(isIdentifier);
|
|
||||||
|
|
||||||
ExpressionPointer expression;
|
|
||||||
|
|
||||||
if (expressionIdentifier == "at"
|
|
||||||
|| expressionIdentifier == "=")
|
|
||||||
{
|
|
||||||
throwUnsupported(context.parser, expressionIdentifier);
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO: implement predicate parsing
|
|
||||||
|
|
||||||
context.parser.expect<std::string>(")");
|
|
||||||
|
|
||||||
return expression;
|
|
||||||
}
|
|
||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
|
||||||
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
@ -51,7 +51,9 @@ PredicatePointer Predicate::parse(std::string name, Context &context,
|
|||||||
// Parse constants
|
// Parse constants
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
const auto *constant = Constant::parseAndFind(context, expressionContext);
|
const auto *constant = (expressionContext.problem == nullptr)
|
||||||
|
? Constant::parseAndFind(context, expressionContext.domain)
|
||||||
|
: Constant::parseAndFind(context, *expressionContext.problem);
|
||||||
auto constantReference = std::make_unique<Reference<Constant>>(constant);
|
auto constantReference = std::make_unique<Reference<Constant>>(constant);
|
||||||
predicate->m_arguments.emplace_back(std::move(constantReference));
|
predicate->m_arguments.emplace_back(std::move(constantReference));
|
||||||
}
|
}
|
||||||
@ -66,6 +68,32 @@ PredicatePointer Predicate::parse(std::string name, Context &context,
|
|||||||
|
|
||||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
PredicatePointer Predicate::parse(std::string name, Context &context, const Problem &problem)
|
||||||
|
{
|
||||||
|
auto predicate = std::make_unique<Predicate>(Predicate());
|
||||||
|
|
||||||
|
predicate->m_name = name;
|
||||||
|
|
||||||
|
context.parser.skipWhiteSpace();
|
||||||
|
|
||||||
|
while (context.parser.currentCharacter() != ')')
|
||||||
|
{
|
||||||
|
if (context.parser.currentCharacter() == '?')
|
||||||
|
throw utils::ParserException(context.parser, "Variables not allowed in this context");
|
||||||
|
|
||||||
|
// Parse objects and constants
|
||||||
|
const auto *constant = Constant::parseAndFind(context, problem);
|
||||||
|
auto constantReference = std::make_unique<Reference<Constant>>(constant);
|
||||||
|
predicate->m_arguments.emplace_back(std::move(constantReference));
|
||||||
|
}
|
||||||
|
|
||||||
|
// TODO: check that signature matches one of the declared ones
|
||||||
|
|
||||||
|
return predicate;
|
||||||
|
}
|
||||||
|
|
||||||
|
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
void Predicate::accept(plasp::pddl::ExpressionVisitor &expressionVisitor) const
|
void Predicate::accept(plasp::pddl::ExpressionVisitor &expressionVisitor) const
|
||||||
{
|
{
|
||||||
expressionVisitor.visit(*this);
|
expressionVisitor.visit(*this);
|
||||||
|
Reference in New Issue
Block a user