match scope

This commit is contained in:
Aleksey Kladov 2018-09-03 01:51:46 +03:00
parent 83e2ab434c
commit 23303cd0f8
3 changed files with 63 additions and 20 deletions

View file

@ -189,7 +189,20 @@ fn compute_expr_scopes(expr: ast::Expr, scopes: &mut FnScopes, scope: ScopeId) {
.chain(e.expr())
.for_each(|expr| compute_expr_scopes(expr, scopes, scope));
}
ast::Expr::MatchExpr(e) => {
if let Some(expr) = e.expr() {
compute_expr_scopes(expr, scopes, scope);
}
for arm in e.match_arm_list().into_iter().flat_map(|it| it.arms()) {
let scope = scopes.new_scope(scope);
for pat in arm.pats() {
scopes.add_bindings(scope, pat);
}
if let Some(expr) = arm.expr() {
compute_expr_scopes(expr, scopes, scope);
}
}
}
_ => {
expr.syntax().children()
.filter_map(ast::Expr::cast)
@ -279,17 +292,17 @@ mod tests {
);
}
// #[test]
// fn test_match() {
// do_check(r"
// fn quux() {
// match () {
// Some(x) => {
// <|>
// }
// };
// }",
// &["x"],
// );
// }
#[test]
fn test_match() {
do_check(r"
fn quux() {
match () {
Some(x) => {
<|>
}
};
}",
&["x"],
);
}
}

View file

@ -842,7 +842,17 @@ impl<'a> AstNode<'a> for MatchArm<'a> {
fn syntax(self) -> SyntaxNodeRef<'a> { self.syntax }
}
impl<'a> MatchArm<'a> {}
impl<'a> MatchArm<'a> {
pub fn pats(self) -> impl Iterator<Item = Pat<'a>> + 'a {
super::children(self)
}
pub fn guard(self) -> Option<MatchGuard<'a>> {
super::child_opt(self)
}
pub fn expr(self) -> Option<Expr<'a>> {
super::child_opt(self)
}
}
// MatchArmList
#[derive(Debug, Clone, Copy)]
@ -860,7 +870,11 @@ impl<'a> AstNode<'a> for MatchArmList<'a> {
fn syntax(self) -> SyntaxNodeRef<'a> { self.syntax }
}
impl<'a> MatchArmList<'a> {}
impl<'a> MatchArmList<'a> {
pub fn arms(self) -> impl Iterator<Item = MatchArm<'a>> + 'a {
super::children(self)
}
}
// MatchExpr
#[derive(Debug, Clone, Copy)]
@ -878,7 +892,13 @@ impl<'a> AstNode<'a> for MatchExpr<'a> {
fn syntax(self) -> SyntaxNodeRef<'a> { self.syntax }
}
impl<'a> MatchExpr<'a> {}
impl<'a> MatchExpr<'a> {pub fn expr(self) -> Option<Expr<'a>> {
super::child_opt(self)
}
pub fn match_arm_list(self) -> Option<MatchArmList<'a>> {
super::child_opt(self)
}
}
// MatchGuard
#[derive(Debug, Clone, Copy)]

View file

@ -370,9 +370,19 @@ Grammar(
options: [ "Block" ]
),
"ReturnExpr": (),
"MatchExpr": (),
"MatchArmList": (),
"MatchArm": (),
"MatchExpr": (
options: [ "Expr", "MatchArmList" ],
),
"MatchArmList": (
collections: [ ["arms", "MatchArm"] ],
),
"MatchArm": (
options: [
[ "guard", "MatchGuard" ],
"Expr",
],
collections: [ [ "pats", "Pat" ] ]
),
"MatchGuard": (),
"StructLit": (),
"NamedFieldList": (),