bnf_rules!

LR(1) parser generator

### Generate LR(1) parser at compilation time. ```rust use bnf_rules::bnf_rules_macro::bnf_rules; // Grammar bnf_rules!( source ::= expr expr ::= factor { "+" factor } factor ::= "-" primary | primary primary ::= "(" expr ")" | number number ::= fn (number_tokenizer) // custom tokenizer with function ); /// Custom tokenizer for numeric literal fn number_tokenizer(source: &Vec, mut current_position: usize) -> usize { let mut iteration_count = 0; loop { let current_char = match source.get(current_position) { Some(ch) => ch.clone(), _ => break }; if !current_char.is_numeric() { break; } iteration_count += 1; current_position += 1; } return iteration_count; // 0 means 'rejected', other means 'accepted' and 'length of token'. } pub fn parse() { // A function named "parse_source" is automatically generated. let ast_node: Result = parse_source("(100 + 200) + -100"); dbg!(ast_node.unwrap()); } ``` ### Usage ```toml bnf_rules = "0.1.4" ``` ### Extended BNF | Form | Semantic | |:------------------------:|:------------------------------------------:| | source | An entire input source. | | ident | A non-terminal symbol named "ident". | | "something" | A terminal symbol for text. | | fn (function_name) | A custom tokenizer with user function.[^1] | | { pattern } | Zero or more repetitions of "pattern". | | \[ pattern \] | "pattern" or null. | | pattern1 | pattern2 | "pattern1" or "pattern2". | | ( patterns ) | A group of patterns. | [^1]: Generic parameters are also available. > Example 1: https://github.com/bea4dev/bnf_rules/blob/master/src/lib.rs > Example 2: https://github.com/bea4dev/catla/blob/master/catla_parser/src/grammar.rs