1 个稳定版本
使用旧的 Rust 2015
2.1.1 | 2019年6月15日 |
---|
#4 in #optimize
在 2 个 crate 中使用 (通过 pest_generator_tmp)
1MB
15K SLoC
pest. 精致的解析器
pest 是一个用 Rust 编写的通用解析器,注重可访问性、正确性和性能。它使用解析表达式语法(或 PEG)作为输入,这与正则表达式在精神上相似,但提供了解析复杂语言所需的增强表达能力。
入门
开始使用 pest 进行解析的推荐方法是阅读官方的 书籍。
其他有用资源
示例
以下是一个列表 alpha-numeric 标识符的语法的示例,其中第一个标识符不以数字开头
alpha = { 'a'..'z' | 'A'..'Z' }
digit = { '0'..'9' }
ident = { (alpha | digit)+ }
ident_list = _{ !digit ~ ident ~ (" " ~ ident)+ }
// ^
// ident_list rule is silent which means it produces no tokens
语法保存在单独的 .pest 文件中,这些文件永远不会与过程代码混合。这导致语言的规范始终是最新的,易于阅读和维护。
有意义的错误报告
基于语法定义,解析器还包括自动错误报告。对于上面的示例,输入 "123"
将导致
thread 'main' panicked at ' --> 1:1
|
1 | 123
| ^---
|
= unexpected digit', src/main.rs:12
而 "ab *"
将导致
thread 'main' panicked at ' --> 1:1
|
1 | ab *
| ^---
|
= expected ident', src/main.rs:12
对 API
可以使用语法自动导出 Parser
实现。解析返回嵌套标记对的迭代器
extern crate pest;
#[macro_use]
extern crate pest_derive;
use pest::Parser;
#[derive(Parser)]
#[grammar = "ident.pest"]
struct IdentParser;
fn main() {
let pairs = IdentParser::parse(Rule::ident_list, "a1 b2").unwrap_or_else(|e| panic!("{}", e));
// Because ident_list is silent, the iterator will contain idents
for pair in pairs {
// A pair is a combination of the rule which matched and a span of input
println!("Rule: {:?}", pair.as_rule());
println!("Span: {:?}", pair.as_span());
println!("Text: {}", pair.as_str());
// A pair can be converted to an iterator of the tokens which make it up:
for inner_pair in pair.into_inner() {
match inner_pair.as_rule() {
Rule::alpha => println!("Letter: {}", inner_pair.as_str()),
Rule::digit => println!("Digit: {}", inner_pair.as_str()),
_ => unreachable!()
};
}
}
}
这会产生以下输出
Rule: ident
Span: Span { start: 0, end: 2 }
Text: a1
Letter: a
Digit: 1
Rule: ident
Span: Span { start: 3, end: 5 }
Text: b2
Letter: b
Digit: 2
其他功能
- 优先级提升
- 输入处理
- 自定义错误
- 在稳定 Rust 上运行
使用 pest 的项目
- pest_meta (自举)
- 大脑
- Chelone
- comrak
- elastic-rs
- graphql-parser
- handlebars-rust
- hexdino
- Huia
- 查询语言(JQL)
- json5-rs
- MT940
- py_literal
- rouler
- RuSh
- rs_pbrt
- stache
- tera
- ui_gen
- ukhasnet-parser
- prisma
特别感谢
向Marius Minea教授的指导和所有pest贡献者表示特别的敬意,其中一些人还是我的朋友。
依赖项
~205KB