1
0
mirror of https://github.com/vlang/v.git synced 2023-08-10 21:13:21 +03:00

checker: fix for $if field.unaliased_typ is $Int { (#16982)

This commit is contained in:
Felipe Pena 2023-01-15 07:27:08 -03:00 committed by GitHub
parent e8e1df6df9
commit 4d2c767dcb
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
2 changed files with 62 additions and 13 deletions

View File

@ -86,24 +86,29 @@ fn (mut c Checker) if_expr(mut node ast.IfExpr) ast.Type {
c.error('invalid `\$if` condition: expected a type', branch.cond.right.pos())
return 0
}
if right is ast.ComptimeType && left is ast.TypeNode {
is_comptime_type_is_expr = true
checked_type := c.unwrap_generic(left.typ)
skip_state = if c.table.is_comptime_type(checked_type, right as ast.ComptimeType) {
.eval
} else {
.skip
}
} else if right is ast.ComptimeType && left is ast.Ident
&& (left as ast.Ident).info is ast.IdentVar {
is_comptime_type_is_expr = true
if var := left.scope.find_var(left.name) {
checked_type := c.unwrap_generic(var.typ)
if right is ast.ComptimeType {
mut checked_type := ast.void_type
if left is ast.TypeNode {
is_comptime_type_is_expr = true
checked_type = c.unwrap_generic(left.typ)
skip_state = if c.table.is_comptime_type(checked_type, right as ast.ComptimeType) {
.eval
} else {
.skip
}
} else if left is ast.Ident && (left as ast.Ident).info is ast.IdentVar {
is_comptime_type_is_expr = true
if var := left.scope.find_var(left.name) {
checked_type = c.unwrap_generic(var.typ)
}
skip_state = if c.table.is_comptime_type(checked_type, right as ast.ComptimeType) {
.eval
} else {
.skip
}
} else if left is ast.SelectorExpr {
comptime_field_name = left.expr.str()
is_comptime_type_is_expr = true
}
} else {
got_type := c.unwrap_generic((right as ast.TypeNode).typ)

View File

@ -0,0 +1,44 @@
type MyArray = []string
type MyString = string
type MyFloat = f64
type MyMap = map[string]string
struct Foo {
a string
b ?string
c MyArray
d MyString
e MyFloat
f MyMap
}
fn test_main() {
mut out := map[string][]string{}
$for field in Foo.fields {
print('${field.name} is ')
$if field.unaliased_typ is $Int {
println('numeric')
out[field.name] << 'numeric'
} $else $if field.unaliased_typ is $Array {
println('array')
out[field.name] << 'array'
} $else $if field.unaliased_typ is $Float {
println('float')
out[field.name] << 'float'
} $else $if field.unaliased_typ is $Map {
println('map')
out[field.name] << 'map'
} $else $if field.unaliased_typ is string || field.unaliased_typ is ?string {
println('string opt? ${field.is_option}')
out[field.name] << 'string'
} $else {
assert false
}
}
assert out['a'][0] == 'string'
assert out['b'][0] == 'string'
assert out['c'][0] == 'array'
assert out['d'][0] == 'string'
assert out['e'][0] == 'float'
assert out['f'][0] == 'map'
}