cgen: gen_str_for_array()

pull/4465/head
yuyi 2020-04-17 22:10:41 +08:00 committed by GitHub
parent 402e55d115
commit 420ecaf31d
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 31 additions and 12 deletions

View File

@ -28,7 +28,6 @@ const (
'vlib/v/tests/option_test.v',
'vlib/v/tests/pointers_test.v',
'vlib/v/tests/repl/repl_test.v',
'vlib/v/tests/string_interpolation_array_of_structs_test.v',
'vlib/v/tests/string_interpolation_variadic_test.v',
'vlib/v/tests/type_test.v',
'vlib/v/tests/valgrind/valgrind_test.v', // ubuntu-musl only

View File

@ -2288,15 +2288,9 @@ fn (var g Gen) string_inter_literal(node ast.StringInterLiteral) {
sym := g.table.get_type_symbol(node.expr_types[i])
if sym.kind == .enum_ {
is_var := match node.exprs[i] {
ast.SelectorExpr {
true
}
ast.Ident {
true
}
else {
false
}
ast.SelectorExpr { true }
ast.Ident { true }
else { false }
}
if is_var {
styp := g.typ(node.expr_types[i])
@ -2319,6 +2313,7 @@ fn (var g Gen) string_inter_literal(node ast.StringInterLiteral) {
}
} else if sym.kind in [.array, .array_fixed] {
styp := g.typ(node.expr_types[i])
g.gen_str_for_type(sym, styp)
g.write('${styp}_str(')
g.expr(expr)
g.write(')')
@ -2873,6 +2868,9 @@ fn (var g Gen) gen_str_for_type(sym table.TypeSymbol, styp string) {
table.Alias {
g.gen_str_default(sym, styp)
}
table.Array, table.ArrayFixed {
g.gen_str_for_array(it, styp)
}
table.Enum {
g.gen_str_for_enum(it, styp)
}
@ -2968,6 +2966,28 @@ fn (var g Gen) gen_str_for_struct(info table.Struct, styp string) {
g.definitions.writeln(', indents.len, indents.str);\n}')
}
fn (var g Gen) gen_str_for_array(info table.Array, styp string) {
s := styp.replace('.', '__')
sym := g.table.get_type_symbol(info.elem_type)
if sym.kind == .struct_ && !sym.has_method('str') {
field_styp := g.typ(info.elem_type)
g.gen_str_for_type(sym, field_styp)
g.definitions.write('string ${s}_str($styp a) {\n')
g.definitions.write('\tstrings__Builder sb = strings__new_builder(a.len * 10);\n')
g.definitions.write('\tstrings__Builder_write(&sb, tos3("["));\n')
g.definitions.write('\tfor (int i = 0; i < a.len; i++) {\n')
g.definitions.write('\t\t${field_styp} it = (*(${field_styp}*)array_get(a, i));\n')
g.definitions.write('\t\tif (i != a.len-1) {\n')
g.definitions.write('\t\t\tstrings__Builder_write(&sb, ${field_styp}_str(it,0));\n')
g.definitions.write('\t\t\tstrings__Builder_write(&sb, tos3(", "));\n')
g.definitions.write('\t\t} else {\n')
g.definitions.write('\t\t\tstrings__Builder_write(&sb, ${field_styp}_str(it,0));\n\t\t}\n\t}\n')
g.definitions.write('\tstrings__Builder_write(&sb, tos3("]"));\n')
g.definitions.write('\treturn strings__Builder_str(&sb);\n')
g.definitions.write('}\n')
}
}
fn (g Gen) type_to_fmt(typ table.Type) string {
sym := g.table.get_type_symbol(typ)
if sym.kind in [.struct_, .array, .array_fixed] {

View File

@ -21,11 +21,11 @@ fn test_default_struct_array_of_structs_interpolation() {
]
s := '$people' // the compiler should generate code for both a) and b)
assert s.contains('Man {')
assert s.contains('name: Superman')
assert s.contains("name: 'Superman'")
assert s.contains('age: 30')
assert s.contains('"being nice"')
assert s.contains('}, Man {')
assert s.contains('name: Bilbo Baggins')
assert s.contains("name: 'Bilbo Baggins'")
assert s.contains('age: 111')
assert s.contains('interests: ["exploring", "hiding"]')
assert s.contains('}]')