patrick
/
plasp
Archived
1
0
Fork 0
This repository has been archived on 2023-07-19. You can view files and clone it, but cannot push or open issues or pull requests.
plasp/lib/pddl/src/pddl/detail/SignatureMatching.cpp

141 lines
4.3 KiB
C++

#include <pddl/detail/SignatureMatching.h>
namespace pddl
{
namespace detail
{
////////////////////////////////////////////////////////////////////////////////////////////////////
//
// SignatureMatching
//
////////////////////////////////////////////////////////////////////////////////////////////////////
bool matches(const ast::PrimitiveTypeDeclaration &lhs, const ast::PrimitiveTypeDeclaration &rhs)
{
// TODO: check if this assumption is correct
// With typing enabled, all objects inherit from “object”
if (rhs.name == "object")
return true;
// Two types match if rhs is lhs or one of its ancestors
if (&lhs == &rhs)
return true;
for (const auto &lhsParentType : lhs.parentTypes)
if (matches(*lhsParentType->declaration, rhs))
return true;
return false;
}
////////////////////////////////////////////////////////////////////////////////////////////////////
bool matches(const ast::PrimitiveTypeDeclaration &lhs, const ast::Either<ast::PrimitiveTypePointer> &rhs)
{
for (const auto &rhsType : rhs.arguments)
if (matches(lhs, *rhsType->declaration))
return true;
return false;
}
////////////////////////////////////////////////////////////////////////////////////////////////////
bool matches(const ast::Either<ast::PrimitiveTypePointer> &lhs, const ast::PrimitiveTypeDeclaration &rhs)
{
if (lhs.arguments.size() != 1)
return false;
// Strictly speaking, a 1-ary either is identical to its argument
return matches(*lhs.arguments[0]->declaration, rhs);
}
////////////////////////////////////////////////////////////////////////////////////////////////////
bool matches(const ast::Either<ast::PrimitiveTypePointer> &lhs, const ast::Either<ast::PrimitiveTypePointer> &rhs)
{
// All of the types in lhs must have a match in rhs
for (const auto &lhsType : lhs.arguments)
if (!matches(*lhsType->declaration, rhs))
return false;
return true;
}
////////////////////////////////////////////////////////////////////////////////////////////////////
template<class T>
bool matches(const T &lhs, const ast::Type &rhs)
{
return rhs.match(
[&](const ast::PrimitiveTypePointer &x){return matches(lhs, *x->declaration);},
[&](const ast::EitherPointer<ast::PrimitiveTypePointer> &x){return matches(lhs, *x);});
}
////////////////////////////////////////////////////////////////////////////////////////////////////
bool matches(const ast::Type &lhs, const ast::Type &rhs)
{
return lhs.match(
[&](const ast::PrimitiveTypePointer &x){return matches(*x->declaration, rhs);},
[&](const ast::EitherPointer<ast::PrimitiveTypePointer> &x){return matches(*x, rhs);});
}
////////////////////////////////////////////////////////////////////////////////////////////////////
bool matches(const ast::VariableDeclaration &lhs, const std::experimental::optional<ast::Type> &rhs)
{
if (!lhs.type && !rhs)
return true;
// If typing is enabled, all objects have to be typed
assert(lhs.type);
assert(rhs);
return matches(lhs.type.value(), rhs.value());
}
////////////////////////////////////////////////////////////////////////////////////////////////////
bool matches(const ast::ConstantDeclaration &lhs, const std::experimental::optional<ast::Type> &rhs)
{
if (!lhs.type && !rhs)
return true;
// If typing is enabled, all objects have to be typed
assert(lhs.type);
assert(rhs);
return matches(lhs.type.value(), rhs.value());
}
////////////////////////////////////////////////////////////////////////////////////////////////////
bool matches(const ast::Term &lhs, const std::experimental::optional<ast::Type> &rhs)
{
return lhs.match([&](const auto &x){return matches(*x->declaration, rhs);});
}
////////////////////////////////////////////////////////////////////////////////////////////////////
bool matches(const std::string &predicateName, const ast::Predicate::Arguments &predicateArguments, const ast::PredicateDeclaration &predicateDeclaration)
{
if (predicateName != predicateDeclaration.name)
return false;
if (predicateArguments.size() != predicateDeclaration.parameters.size())
return false;
for (size_t i = 0; i < predicateArguments.size(); i++)
if (!matches(predicateArguments[i], predicateDeclaration.parameters[i]->type))
return false;
return true;
}
////////////////////////////////////////////////////////////////////////////////////////////////////
}
}