match: implement exhaustive match for bool values (#7761)
							parent
							
								
									73f41f9a2a
								
							
						
					
					
						commit
						9ac237d9c0
					
				| 
						 | 
					@ -3673,11 +3673,10 @@ pub fn (mut c Checker) match_expr(mut node ast.MatchExpr) table.Type {
 | 
				
			||||||
	return ret_type
 | 
						return ret_type
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
fn (mut c Checker) match_exprs(mut node ast.MatchExpr, type_sym table.TypeSymbol) {
 | 
					fn (mut c Checker) match_exprs(mut node ast.MatchExpr, cond_type_sym table.TypeSymbol) {
 | 
				
			||||||
	// branch_exprs is a histogram of how many times
 | 
						// branch_exprs is a histogram of how many times
 | 
				
			||||||
	// an expr was used in the match
 | 
						// an expr was used in the match
 | 
				
			||||||
	mut branch_exprs := map[string]int{}
 | 
						mut branch_exprs := map[string]int{}
 | 
				
			||||||
	cond_type_sym := c.table.get_type_symbol(node.cond_type)
 | 
					 | 
				
			||||||
	for branch_i, _ in node.branches {
 | 
						for branch_i, _ in node.branches {
 | 
				
			||||||
		mut branch := node.branches[branch_i]
 | 
							mut branch := node.branches[branch_i]
 | 
				
			||||||
		mut expr_types := []ast.Type{}
 | 
							mut expr_types := []ast.Type{}
 | 
				
			||||||
| 
						 | 
					@ -3860,27 +3859,37 @@ fn (mut c Checker) match_exprs(mut node ast.MatchExpr, type_sym table.TypeSymbol
 | 
				
			||||||
	// by listing all variants or values
 | 
						// by listing all variants or values
 | 
				
			||||||
	mut is_exhaustive := true
 | 
						mut is_exhaustive := true
 | 
				
			||||||
	mut unhandled := []string{}
 | 
						mut unhandled := []string{}
 | 
				
			||||||
	match mut type_sym.info {
 | 
						if node.cond_type == table.bool_type {
 | 
				
			||||||
		table.SumType {
 | 
							variants := ['true', 'false']
 | 
				
			||||||
			for v in type_sym.info.variants {
 | 
							for v in variants {
 | 
				
			||||||
				v_str := c.table.type_to_str(v)
 | 
								if v !in branch_exprs {
 | 
				
			||||||
				if v_str !in branch_exprs {
 | 
									is_exhaustive = false
 | 
				
			||||||
					is_exhaustive = false
 | 
									unhandled << '`$v`'
 | 
				
			||||||
					unhandled << '`$v_str`'
 | 
					 | 
				
			||||||
				}
 | 
					 | 
				
			||||||
			}
 | 
								}
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
		//
 | 
						} else {
 | 
				
			||||||
		table.Enum {
 | 
							match mut cond_type_sym.info {
 | 
				
			||||||
			for v in type_sym.info.vals {
 | 
								table.SumType {
 | 
				
			||||||
				if v !in branch_exprs {
 | 
									for v in cond_type_sym.info.variants {
 | 
				
			||||||
					is_exhaustive = false
 | 
										v_str := c.table.type_to_str(v)
 | 
				
			||||||
					unhandled << '`.$v`'
 | 
										if v_str !in branch_exprs {
 | 
				
			||||||
 | 
											is_exhaustive = false
 | 
				
			||||||
 | 
											unhandled << '`$v_str`'
 | 
				
			||||||
 | 
										}
 | 
				
			||||||
				}
 | 
									}
 | 
				
			||||||
			}
 | 
								}
 | 
				
			||||||
		}
 | 
								//
 | 
				
			||||||
		else {
 | 
								table.Enum {
 | 
				
			||||||
			is_exhaustive = false
 | 
									for v in cond_type_sym.info.vals {
 | 
				
			||||||
 | 
										if v !in branch_exprs {
 | 
				
			||||||
 | 
											is_exhaustive = false
 | 
				
			||||||
 | 
											unhandled << '`.$v`'
 | 
				
			||||||
 | 
										}
 | 
				
			||||||
 | 
									}
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								else {
 | 
				
			||||||
 | 
									is_exhaustive = false
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	mut else_branch := node.branches[node.branches.len - 1]
 | 
						mut else_branch := node.branches[node.branches.len - 1]
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
| 
						 | 
					@ -21,7 +21,6 @@ fn test_assign_multi_expr_func() {
 | 
				
			||||||
	g, h := match true {
 | 
						g, h := match true {
 | 
				
			||||||
		true { multireturner(0, 'good') }
 | 
							true { multireturner(0, 'good') }
 | 
				
			||||||
		false { multireturner(100, 'bad') }
 | 
							false { multireturner(100, 'bad') }
 | 
				
			||||||
		else { multireturner(200, 'bad') }
 | 
					 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	assert g == 1
 | 
						assert g == 1
 | 
				
			||||||
	assert h == 'good'
 | 
						assert h == 'good'
 | 
				
			||||||
| 
						 | 
					@ -36,7 +35,6 @@ fn test_assign_multi_expr() {
 | 
				
			||||||
	a,b,c := match false {
 | 
						a,b,c := match false {
 | 
				
			||||||
		true { 1,2,3 }
 | 
							true { 1,2,3 }
 | 
				
			||||||
		false { 4,5,6 }
 | 
							false { 4,5,6 }
 | 
				
			||||||
		else { 7,8,9 }
 | 
					 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
	assert a == 4
 | 
						assert a == 4
 | 
				
			||||||
	assert b == 5
 | 
						assert b == 5
 | 
				
			||||||
| 
						 | 
					
 | 
				
			||||||
		Loading…
	
		Reference in New Issue