Header lexy/action/parse.hpp

Class lexy::parse_result

lexy/action/parse.hpp
namespace lexy
{
    template <typename T, typename ErrorCallback>
    class parse_result
    {
    public:
        using value_type     = T;
        using error_callback = ErrorCallback;
        using error_type     = see-below;

        //=== status ===//
        constexpr explicit operator bool() const noexcept
        {
            return is_success();
        }

        constexpr bool is_success()         const noexcept;
        constexpr bool is_error()           const noexcept;
        constexpr bool is_recovered_error() const neoxcept;
        constexpr bool is_fatal_error()     const noexcept;

        //=== value ===//
        constexpr bool has_value() const noexcept;

        constexpr const value_type& value() const& noexcept;
        constexpr value_type&&      value() &&     noexcept;

        //=== error list ===//
        constexpr std::size_t error_count() const noexcept;

        constexpr const error_type& errors() const& noexcept;
        constexpr error_type&&      errors() &&     noexcept;
    };
}

The result of lexy::parse.

It stores the status of the action, the value producing during parsing, and the final error list of the error callback, which has type error_type.

Note
The status and error list are identical to lexy::validate_result.

Status

lexy/action/parse.hpp
constexpr explicit operator bool() const noexcept
{
    return is_success();
}

constexpr bool is_success()         const noexcept; (1)
constexpr bool is_error()           const noexcept; (2)
constexpr bool is_recovered_error() const neoxcept; (3)
constexpr bool is_fatal_error()     const noexcept; (4)
  1. Returns true if parsing succeeded without raising any errors, false otherwise.

  2. Returns true if at least one error occurred during parsing, false otherwise.

  3. Returns true if at least one error occurred during parsing but it could recover from all of them, false otherwise.

  4. Returns true if at least one error occurred during parsing that could not be recovered, false otherwise.

Note
is_error() is equivalent to is_recovered_error() || is_fatal_error(), and is_success() is !is_error().

Value

lexy/action/parse.hpp
constexpr bool has_value() const noexcept;           (1)

constexpr const value_type& value() const& noexcept; (2)
constexpr value_type&&      value() &&     noexcept; (2)
  1. Returns true if parsing could produce a value, false otherwise. It produces a value when parsing succeeded (is_success() == true), or when it could recover from all errors (is_recovered_error() == true).

  2. Returns the value producing during parsing, requires has_value() == true.

Caution
If has_value() == true but is_success() == false (i.e. is_recovered_error() == true), the value was produced after recovering from an error. This means that some invariants that would be satisfied for a well-formed input are not necessarily satisfied now. For example, in a well-formed input a lexy::dsl::identifier is not reserved, but after recovery a reserved identifier is produced.

Error list

lexy/action/parse.hpp
constexpr std::size_t error_count() const noexcept; (1)

constexpr const error_type& errors() const& noexcept; (2)
constexpr error_type&&      errors() &&     noexcept; (2)
  1. If error_type is std::size_t, returns errors(). Otherwise, returns errors().size().

  2. The final value of the ErrorCallback, unchanged.

If is_success() == true, error_count() == 0 and errors() returns the result of the sink callback that is finished without ever invoking it.

Action lexy::parse

lexy/action/parse.hpp
namespace lexy
{
    template <production Production>
    constexpr auto parse(const input auto& input,
                         error-callback auto error_callback)
      -> parse_result<see-below, decltype(error_callback)>;

    template <production Production, typename State>
    constexpr auto parse(const input auto& input, const State& state,
                         error-callback auto error_callback)
      -> parse_result<see-below, decltype(error_callback)>;
}

An action that parses Production on input and produces a value.

It parses Production on input. All values produced during parsing are forwarded to the Production::value callback; all errors raised are forwarded to the error callback. Returns the lexy::parse_result containing the final value and the result of the error callback.

It requires that every production P of the grammar reachable by Production has a ::value callback. It is used as follows:

  1. P::rule does not contain a rule that requires a sink (e.g. lexy::dsl::list). Then P::value must be a callback. It will be invoked with all values produced by P::rule; it’s result is the result of parsing P.

  2. P::rule contains a rule that requires a sink and no other rule produces a value. Then P::value must be a sink, and it will be used to collect the values. If P::value is a also a callback that accepts the result of the sink, the result of parsing P is the P::value invoked with the sink result. Otherwise, the result of parsing P is the result of the sink.

  3. P::rule contains both rules that require a sink and other rules produce values. Then P::value must be both a callback and a sink. The sink is used to collect the values, its final result is forwarded together with all other values to the callback. The result of parsing P is the result of the callback.

If P is reached by a lexy::dsl::p or lexy::dsl::recurse rule, they produce the result of parsing P as its value. If P is the top-level Production, its result is returned as the final value of the lexy::parse_result.

The second overload of lexy::parse accepts a state, which is an arbitrary object. If P::value is a callback that accepts state as context, or a sink that accepts state as the argument to .sink(), it will be passed to them.

Tip
Use lexy::operator>> to combine a sink and a callback in case 3 above.
Tip
Use lexy::bind and lexy::bind_sink with the placeholder lexy::parse_state to access the state object in existing callbacks.

See also