From 0e95e4d7b46cc833d9e7ca1d9d29ae3cfbfdc992 Mon Sep 17 00:00:00 2001 From: yuyi Date: Fri, 29 Oct 2021 00:03:17 +0800 Subject: [PATCH] ast, cgen: fix generic method str() overload (#12330) --- vlib/v/ast/types.v | 7 ++++++- vlib/v/gen/c/auto_str_methods.v | 5 ++++- vlib/v/tests/generics_method_str_overload_test.v | 15 +++++++++++++++ 3 files changed, 25 insertions(+), 2 deletions(-) create mode 100644 vlib/v/tests/generics_method_str_overload_test.v diff --git a/vlib/v/ast/types.v b/vlib/v/ast/types.v index d0b0452945..e61c089f0f 100644 --- a/vlib/v/ast/types.v +++ b/vlib/v/ast/types.v @@ -1186,6 +1186,11 @@ pub fn (t &TypeSymbol) has_method(name string) bool { return true } +pub fn (t &TypeSymbol) has_method_with_generic_parent(name string) bool { + t.find_method_with_generic_parent(name) or { return false } + return true +} + pub fn (t &TypeSymbol) find_method(name string) ?Fn { for method in t.methods { if method.name == name { @@ -1240,7 +1245,7 @@ pub fn (t &TypeSymbol) str_method_info() (bool, bool, int) { mut has_str_method := false mut expects_ptr := false mut nr_args := 0 - if sym_str_method := t.find_method('str') { + if sym_str_method := t.find_method_with_generic_parent('str') { has_str_method = true nr_args = sym_str_method.params.len if nr_args > 0 { diff --git a/vlib/v/gen/c/auto_str_methods.v b/vlib/v/gen/c/auto_str_methods.v index 7da606605c..08f30a2f73 100644 --- a/vlib/v/gen/c/auto_str_methods.v +++ b/vlib/v/gen/c/auto_str_methods.v @@ -144,6 +144,9 @@ fn (mut g Gen) get_str_fn(typ ast.Type) string { str_fn_name = styp_to_str_fn_name(sym.name) } } + if sym.has_method_with_generic_parent('str') && mut sym.info is ast.Struct { + str_fn_name = g.generic_fn_name(sym.info.concrete_types, str_fn_name, false) + } g.str_types << StrType{ typ: unwrapped styp: styp @@ -157,7 +160,7 @@ fn (mut g Gen) final_gen_str(typ StrType) { } g.generated_str_fns << typ sym := g.table.get_type_symbol(typ.typ) - if sym.has_method('str') && !typ.typ.has_flag(.optional) { + if sym.has_method_with_generic_parent('str') && !typ.typ.has_flag(.optional) { return } styp := typ.styp diff --git a/vlib/v/tests/generics_method_str_overload_test.v b/vlib/v/tests/generics_method_str_overload_test.v new file mode 100644 index 0000000000..7ca5835bc1 --- /dev/null +++ b/vlib/v/tests/generics_method_str_overload_test.v @@ -0,0 +1,15 @@ +struct Gen { + data G + id int + size int +} + +fn (g Gen) str() string { + return 'Gen $g.id, $g.data, ${g.size}.' +} + +fn test_generics_method_str_overload() { + mut g := Gen{'Gen', 0, 10} + println(g) + assert '$g' == 'Gen 0, Gen, 10.' +}