Refactored parsing variables, constants, and predicates.
This commit is contained in:
parent
0de5b9eb56
commit
51249fd678
@ -16,6 +16,7 @@ namespace detail
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
std::experimental::optional<ast::ConstantPointer> testParsingConstant(Context &context, ASTContext &astContext);
|
||||
ast::ConstantPointer parseConstant(Context &context, ASTContext &astContext);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -17,6 +17,7 @@ namespace detail
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// TODO: rename consistently
|
||||
std::experimental::optional<ast::PredicatePointer> parsePredicate(Context &context, ASTContext &astContext, VariableStack &variableStack);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -16,6 +16,8 @@ namespace detail
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// TODO: find consistent naming scheme
|
||||
std::experimental::optional<ast::VariablePointer> testParsingVariable(Context &context, VariableStack &variableStack);
|
||||
ast::VariablePointer parseVariable(Context &context, VariableStack &variableStack);
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -30,48 +30,8 @@ std::experimental::optional<ast::ConstantPointer> findConstant(const std::string
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// TODO: remove if unneeded
|
||||
ast::ConstantPointer parseConstant(Context &context, ast::Domain &domain)
|
||||
std::experimental::optional<ast::ConstantPointer> findConstant(const std::string &constantName, ASTContext &astContext)
|
||||
{
|
||||
auto &tokenizer = context.tokenizer;
|
||||
const auto constantName = tokenizer.getIdentifier();
|
||||
|
||||
auto constant = findConstant(constantName, domain.constants);
|
||||
|
||||
if (constant)
|
||||
return std::move(constant.value());
|
||||
|
||||
throw ParserException(tokenizer.location(), "constant “" + constantName + "” used but never declared");
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
// TODO: remove if unneeded
|
||||
ast::ConstantPointer parseConstant(Context &context, ast::Problem &problem)
|
||||
{
|
||||
auto &tokenizer = context.tokenizer;
|
||||
const auto constantName = tokenizer.getIdentifier();
|
||||
|
||||
auto constant = findConstant(constantName, problem.domain->constants);
|
||||
|
||||
if (constant)
|
||||
return std::move(constant.value());
|
||||
|
||||
auto object = findConstant(constantName, problem.objects);
|
||||
|
||||
if (object)
|
||||
return std::move(object.value());
|
||||
|
||||
throw ParserException(tokenizer.location(), "constant “" + constantName + "” used but never declared");
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
ast::ConstantPointer parseConstant(Context &context, ASTContext &astContext)
|
||||
{
|
||||
auto &tokenizer = context.tokenizer;
|
||||
const auto constantName = tokenizer.getIdentifier();
|
||||
|
||||
auto constant = findConstant(constantName, astContext.domain->constants);
|
||||
|
||||
if (constant)
|
||||
@ -85,7 +45,37 @@ ast::ConstantPointer parseConstant(Context &context, ASTContext &astContext)
|
||||
return std::move(constant.value());
|
||||
}
|
||||
|
||||
throw ParserException(tokenizer.location(), "constant “" + constantName + "” used but never declared");
|
||||
return std::experimental::nullopt;
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
std::experimental::optional<ast::ConstantPointer> testParsingConstant(Context &context, ASTContext &astContext)
|
||||
{
|
||||
auto &tokenizer = context.tokenizer;
|
||||
|
||||
const auto constantName = tokenizer.getIdentifier();
|
||||
auto constant = findConstant(constantName, astContext);
|
||||
|
||||
if (!constant)
|
||||
return std::experimental::nullopt;
|
||||
|
||||
return std::move(constant.value());
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
ast::ConstantPointer parseConstant(Context &context, ASTContext &astContext)
|
||||
{
|
||||
auto &tokenizer = context.tokenizer;
|
||||
|
||||
const auto constantName = tokenizer.getIdentifier();
|
||||
auto constant = findConstant(constantName, astContext);
|
||||
|
||||
if (!constant)
|
||||
throw ParserException(tokenizer.location(), "undeclared constant “" + constantName + "”");
|
||||
|
||||
return std::move(constant.value());
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
@ -20,11 +20,11 @@ std::experimental::optional<ast::PredicatePointer> parsePredicate(Context &conte
|
||||
{
|
||||
auto &tokenizer = context.tokenizer;
|
||||
|
||||
const auto position = tokenizer.position();
|
||||
const auto previousPosition = tokenizer.position();
|
||||
|
||||
if (!tokenizer.testAndSkip<std::string>("("))
|
||||
{
|
||||
tokenizer.seek(position);
|
||||
tokenizer.seek(previousPosition);
|
||||
return std::experimental::nullopt;
|
||||
}
|
||||
|
||||
@ -53,14 +53,31 @@ std::experimental::optional<ast::PredicatePointer> parsePredicate(Context &conte
|
||||
// Parse arguments
|
||||
while (tokenizer.currentCharacter() != ')')
|
||||
{
|
||||
// Parse variables
|
||||
if (tokenizer.currentCharacter() == '?')
|
||||
arguments.emplace_back(parseVariable(context, variableStack));
|
||||
// Parse constants
|
||||
else
|
||||
arguments.emplace_back(parseConstant(context, astContext));
|
||||
// Parse argument if it is a variable
|
||||
auto variable = testParsingVariable(context, variableStack);
|
||||
|
||||
tokenizer.skipWhiteSpace();
|
||||
if (variable)
|
||||
{
|
||||
arguments.emplace_back(std::move(variable.value()));
|
||||
|
||||
tokenizer.skipWhiteSpace();
|
||||
continue;
|
||||
}
|
||||
|
||||
// Parse argument if it is a constant
|
||||
auto constant = testParsingConstant(context, astContext);
|
||||
|
||||
if (constant)
|
||||
{
|
||||
arguments.emplace_back(std::move(constant.value()));
|
||||
|
||||
tokenizer.skipWhiteSpace();
|
||||
continue;
|
||||
}
|
||||
|
||||
// If argument is neither variable nor constant, this is not a valid predicate
|
||||
tokenizer.seek(previousPosition);
|
||||
return std::experimental::nullopt;
|
||||
}
|
||||
|
||||
//const auto &predicates = astContext.domain->predicates;
|
||||
|
@ -14,14 +14,53 @@ namespace detail
|
||||
//
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
ast::VariablePointer parseVariable(Context &context, VariableStack &variableStack)
|
||||
std::experimental::optional<std::string> testParsingVariableName(Context &context)
|
||||
{
|
||||
auto &tokenizer = context.tokenizer;
|
||||
|
||||
if (!tokenizer.testAndReturn<std::string>("?"))
|
||||
return std::experimental::nullopt;
|
||||
|
||||
tokenizer.expect<std::string>("?");
|
||||
|
||||
return tokenizer.getIdentifier();
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
std::string parseVariableName(Context &context)
|
||||
{
|
||||
auto &tokenizer = context.tokenizer;
|
||||
|
||||
tokenizer.expect<std::string>("?");
|
||||
|
||||
const auto variableName = tokenizer.getIdentifier();
|
||||
return tokenizer.getIdentifier();
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
std::experimental::optional<ast::VariablePointer> testParsingVariable(Context &context, VariableStack &variableStack)
|
||||
{
|
||||
auto variableName = testParsingVariableName(context);
|
||||
|
||||
if (!variableName)
|
||||
return std::experimental::nullopt;
|
||||
|
||||
auto variableDeclaration = variableStack.findVariableDeclaration(variableName.value());
|
||||
|
||||
if (!variableDeclaration)
|
||||
return std::experimental::nullopt;
|
||||
|
||||
return std::make_unique<ast::Variable>(variableDeclaration.value());
|
||||
}
|
||||
|
||||
////////////////////////////////////////////////////////////////////////////////////////////////////
|
||||
|
||||
ast::VariablePointer parseVariable(Context &context, VariableStack &variableStack)
|
||||
{
|
||||
auto &tokenizer = context.tokenizer;
|
||||
|
||||
auto variableName = parseVariableName(context);
|
||||
auto variableDeclaration = variableStack.findVariableDeclaration(variableName);
|
||||
|
||||
if (!variableDeclaration)
|
||||
|
Reference in New Issue
Block a user