diff options
author | Marcus Klaas de Vries <[email protected]> | 2019-01-06 20:39:36 +0000 |
---|---|---|
committer | Marcus Klaas de Vries <[email protected]> | 2019-01-06 21:17:54 +0000 |
commit | 82d9a77dade454ee8d09f198fa839e7755ff7bfb (patch) | |
tree | 791b3c0ee6069a06896c815795ff7e86877887df /crates/ra_hir/src/ty.rs | |
parent | 4fc233a02e8dc07619a969400c445ec47c2b1a9d (diff) |
Touch up type inference for boolean operators
Also try to infer its subexpressions and set type expectations
whenever possible.
Diffstat (limited to 'crates/ra_hir/src/ty.rs')
-rw-r--r-- | crates/ra_hir/src/ty.rs | 36 |
1 files changed, 29 insertions, 7 deletions
diff --git a/crates/ra_hir/src/ty.rs b/crates/ra_hir/src/ty.rs index 718e193f7..8f56cdb15 100644 --- a/crates/ra_hir/src/ty.rs +++ b/crates/ra_hir/src/ty.rs | |||
@@ -526,6 +526,20 @@ struct InferenceContext<'a, D: HirDatabase> { | |||
526 | return_ty: Ty, | 526 | return_ty: Ty, |
527 | } | 527 | } |
528 | 528 | ||
529 | // helper function that determines whether a binary operator | ||
530 | // always returns a boolean | ||
531 | fn is_boolean_operator(op: BinOp) -> bool { | ||
532 | match op { | ||
533 | BinOp::BooleanOr | ||
534 | | BinOp::BooleanAnd | ||
535 | | BinOp::EqualityTest | ||
536 | | BinOp::LesserEqualTest | ||
537 | | BinOp::GreaterEqualTest | ||
538 | | BinOp::LesserTest | ||
539 | | BinOp::GreaterTest => true, | ||
540 | } | ||
541 | } | ||
542 | |||
529 | impl<'a, D: HirDatabase> InferenceContext<'a, D> { | 543 | impl<'a, D: HirDatabase> InferenceContext<'a, D> { |
530 | fn new( | 544 | fn new( |
531 | db: &'a D, | 545 | db: &'a D, |
@@ -907,13 +921,21 @@ impl<'a, D: HirDatabase> InferenceContext<'a, D> { | |||
907 | } | 921 | } |
908 | ast::Expr::RangeExpr(_e) => Ty::Unknown, | 922 | ast::Expr::RangeExpr(_e) => Ty::Unknown, |
909 | ast::Expr::BinExpr(e) => match e.op() { | 923 | ast::Expr::BinExpr(e) => match e.op() { |
910 | Some(BinOp::BooleanOr) | 924 | Some(op) => { |
911 | | Some(BinOp::BooleanAnd) | 925 | let subtype_expectation = match op { |
912 | | Some(BinOp::EqualityTest) | 926 | BinOp::BooleanAnd | BinOp::BooleanOr => Expectation::has_type(Ty::Bool), |
913 | | Some(BinOp::LesserEqualTest) | 927 | _ => Expectation::none(), |
914 | | Some(BinOp::GreaterEqualTest) | 928 | }; |
915 | | Some(BinOp::LesserTest) | 929 | let (lhs, rhs) = e.sub_exprs(); |
916 | | Some(BinOp::GreaterTest) => Ty::Bool, | 930 | let _lhs_ty = self.infer_expr_opt(lhs, &subtype_expectation)?; |
931 | let _rhs_ty = self.infer_expr_opt(rhs, &subtype_expectation)?; | ||
932 | |||
933 | if is_boolean_operator(op) { | ||
934 | Ty::Bool | ||
935 | } else { | ||
936 | Ty::Unknown | ||
937 | } | ||
938 | } | ||
917 | _ => Ty::Unknown, | 939 | _ => Ty::Unknown, |
918 | }, | 940 | }, |
919 | ast::Expr::Literal(_e) => Ty::Unknown, | 941 | ast::Expr::Literal(_e) => Ty::Unknown, |