Header lexy/grammar.hpp

Traits and definitions for the grammar.

Grammar traits

lexy/grammar.hpp
namespace lexy
{
    template <typename T>
    constexpr bool is_production;  (1)

    template <typename T>
    constexpr bool is_rule;        (2)
    template <typename T>
    constexpr bool is_branch_rule; (3)
    template <typename T>
    constexpr bool is_unconditional_branch_rule; (4)
    template <typename T>
    constexpr bool is_token_rule;  (5)

    template <typename T>
    constexpr bool is_literal_rule; (6)
    template <typename T>
    constexpr bool is_literal_set_rule; (7)
    template <typename T>
    constexpr bool is_char_class_rule; (8)

    template <typename T>
    constexpr bool is_separator; (9)
}
  1. Whether or not T is a production, i.e. it has a ::rule member.

  2. Whether or not T is a rule.

  3. Whether or not T is a branch rule.

  4. Whether or not T is an unconditional branch rule (e.g. lexy::dsl::else_).

  5. Whether or not T is a token rule.

  6. Whether or not T is a literal rule.

  7. Whether or not T is a lexy::dsl::literal_set rule.

  8. Whether or not T is a char class rule.

  9. Whether or not T is a separator (lexy::dsl::sep and lexy::dsl::trailing_sep).

Function lexy::production_name

lexy/grammar.hpp
namespace lexy
{
    template <production Production>
    consteval const char* production_name();
}

Returns the name of the production.

By default, it is the type name of Production after removing the top-level namespace. This can be overridden by Production::name() or Production::name.

Trait lexy::production_rule

lexy/grammar.hpp
namespace lexy
{
    template <production Production>
    using production_rule = std::decay_t<decltype(Production::rule)>;
}

Returns the type of the rule of production, i.e. the type of Production::rule.

Trait lexy::production_whitespace

lexy/grammar.hpp
namespace lexy
{
    template <production Production, production WhitespaceProduction>
    using production_whitespace = see-below;
}

Returns the type of the whitespace rule of Production given its last parent WhitespaceProduction.

It is determined as follows:

  1. If Production::whitespace is valid, returns the decayed type of that.

  2. If WhitespaceProduction::whitespace is valid, returns the decayed type of that.

  3. Otherwise, returns void.

This is used by lexy::dsl::whitespace during automatic whitespace skipping.

Callback lexy::production_value_callback

lexy/grammar.hpp
namespace lexy
{
    template <production Production, typename ParseState = void>
    class production_value_callback
    {
    public:
        constexpr explicit production_value_callback(const ParseState&);

        using return_type = see-below;

        constexpr sink auto sink() const;

        template <typename ... Args>
        constexpr return_type operator()(Args&&... args);
    };
}

A callback and sink for the specified Production.

It wraps an underlying callback/sink, which is determined as follows:

  1. ParseState is non-void and the call state.value_of(Production{}) is well-formed. It will use the result as the underlying callback/sink.

  2. ParseState is non-void but state.value_of(Production{}) is ill-formed. It will use Production::value as the underlying callback/sink, passing the parse state to .sink() and as state parameter to the callback.

  3. ParseState is void. It will use Production::value as the underlying callback/sink.

The behavior of the member functions depends on three cases:

  1. If the underlying callback/sink is a callback, return_type is its return type, .sink() is ill-formed and operator() forwards to Production::value.operator().

  2. If the underlying callback/sink is a sink, return_type is its return type, .sink() forwards to Production::value.sink(), and operator() accepts the return type of the sink and forwards it unchanged.

  3. If the underlying callback/sink is both a callback and a sink, return_type is the return type of the callback, .sink() forwards to the sink, and operator() to the callback.

Tip
Use lexy::operator>> to combine a sink and a callback in one Production::value.

Function lexy::max_recursion_depth

lexy/grammar.hpp
namespace lexy
{
    template <production EntryProduction>
    consteval std::size_t max_recursion_depth();
}

Returns the maximum recursion depth of a grammar given its entry production.

If the entry production has a static std::size_t member named max_recursion_depth (i.e. EntryProduction::max_recursion_depth is well-formed), returns that value. Otherwise returns an implementation-defined "big" value (currently 1024).

If the recursion depth of lexy::dsl::recurse exceeds this value, an error is raised.

Class lexy::token_production

lexy/grammar.hpp
namespace lexy
{
    struct token_production
    {};

    template <production Production>
    constexpr bool is_token_production = std::is_base_of_v<token_production, Production>;
}

Base class to indicate that a production is conceptually a token. This inhibits whitespace skipping (directly) inside the production.

Class lexy::transparent_production

lexy/grammar.hpp
namespace lexy
{
    struct transparent_production
    {};

    template <production Production>
    constexpr bool is_transparent_production = std::is_base_of_v<transparent_production, Production>;
}

Base class to indicate that this production should not show up in the parse tree.

In the parse tree, there will be no separate node for Production. Instead, all child nodes of Production are added to its parent node.

See also