コード例 #1
0
def test_extend_grammar():
    grammar1 = Grammar()
    grammar1.add_pattern(grammar1.add_token('A'), 'a+')
    grammar1.add_pattern(grammar1.add_token('B'), 'b+')
    grammar1.add_pattern(grammar1.add_token('C'), 'c+')
    grammar1.add_parselet('expr', kind=ParseletKind.Pratt)

    grammar2 = Grammar()
    grammar2.add_pattern(grammar2.add_token('A'), '_a+')
    grammar2.add_pattern(grammar2.add_token('B'), '_b+')
    grammar2.add_parselet('expr', kind=ParseletKind.Pratt)

    result = Grammar()
    initial_count = len(result.symbols)
    result.extend(grammar1)
    result.extend(grammar2)

    assert 'A' in result.tokens
    assert 'B' in result.tokens
    assert 'C' in result.tokens
    assert len(result.symbols) == initial_count + 4
    assert len(result.parselets) == 1
    assert len(result.patterns) == 5
    assert {pattern.pattern.pattern
            for pattern in result.patterns
            } == {'a+', '_a+', 'b+', '_b+', 'c+'}
コード例 #2
0
def test_extend_implicit_grammar():
    grammar1 = Grammar()
    grammar1.add_implicit('(')
    result = Grammar()
    result.extend(grammar1)
    assert result.patterns[0].token_id == result.tokens['(']
    assert result.patterns[0].priority == -len('(')
    assert result.patterns[0].is_implicit
コード例 #3
0
def create_combinator_grammar() -> Grammar:
    """
    Create grammar for parse combinator definition

    P.S. This grammar is used for bootstrap process of initial grammar, e.g. definition of combinators in grammar
    """
    grammar = Grammar()
    grammar.extend(create_core_grammar())

    # tokens
    name_id = grammar.tokens['Name']
    string_id = grammar.tokens['String']
    number_id = grammar.tokens['Integer']
    colon_id = grammar.add_implicit(':')
    parent_open_id = grammar.tokens['(']
    parent_close_id = grammar.tokens[')']
    square_open_id = grammar.tokens['[']
    square_close_id = grammar.tokens[']']
    curly_open_id = grammar.tokens['{']
    curly_close_id = grammar.tokens['}']
    less_id = grammar.tokens['<']
    great_id = grammar.tokens['>']

    # parse combinator definition
    comb_id = grammar.add_parselet('combinator', result_type=CombinatorNode)
    seq_id = grammar.add_parselet('combinator_sequence', result_type=SequenceNode)

    # combinator := name: Name ":" combinator=combinator            ; named variable
    grammar.add_parser(
        comb_id,
        make_sequence(make_named('name', name_id), colon_id, make_named('combinator', comb_id)),
        make_ctor(NamedNode)
    )

    # combinator := name: Name  [ '<' priority: Number '>' ]        ; reference to parselet or token
    grammar.add_parser(
        comb_id,
        make_sequence(make_named('name', name_id), make_optional(less_id, make_named('priority', number_id), great_id)),
        make_ctor(ReferenceNode)
    )

    # combinator := value: String                                   ; reference to implicit token
    grammar.add_parser(comb_id, make_named('value', string_id), make_ctor(ImplicitNode))

    # combinator := '[' combinator: combinator_sequence ']'         ; optional combinator
    grammar.add_parser(
        comb_id,
        make_sequence(square_open_id, make_named('combinator', seq_id), square_close_id),
        make_ctor(OptionalNode)
    )

    # combinator := '{' combinator: combinator_sequence '}'         ; repeat combinator
    grammar.add_parser(
        comb_id,
        make_sequence(curly_open_id, make_named('combinator', seq_id), curly_close_id),
        make_ctor(RepeatNode)
    )

    # combinator := '(' combinator: combinator_sequence ')'         ; parenthesis combinator
    grammar.add_parser(
        comb_id,
        make_sequence(parent_open_id, make_named('combinator', seq_id), parent_close_id),
        make_return_variable('combinator')
    )

    # combinator_sequence := combinators:combinator combinators:{ combinator }              ; sequence combinator
    grammar.add_parser(
        seq_id,
        make_sequence(make_named('combinators', comb_id), make_named('combinators', make_repeat(comb_id))),
        make_ctor(SequenceNode)
    )

    return grammar