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

ast, fmt: simplify fmt.fn_decl() (#19054)

This commit is contained in:
yuyi 2023-08-04 21:54:16 +08:00 committed by GitHub
parent d91c7f1b3b
commit 4cf8328f71
No known key found for this signature in database
GPG Key ID: 4AEE18F83AFDEB23
3 changed files with 47 additions and 133 deletions

View File

@ -89,6 +89,13 @@ pub fn (t &Table) stringify_fn_decl(node &FnDecl, cur_mod string, m2a map[string
f.write_string('pub ')
}
f.write_string('fn ')
pre_comments := node.comments.filter(it.pos.pos < node.name_pos.pos)
if pre_comments.len > 0 {
write_comments(pre_comments, mut f)
if !f.last_n(1)[0].is_space() {
f.write_string(' ')
}
}
if node.is_method {
f.write_string('(')
mut styp := util.no_cur_mod(t.type_to_code(node.receiver.typ.clear_flag(.shared_f)),
@ -211,13 +218,50 @@ fn (t &Table) stringify_fn_after_name(node &FnDecl, mut f strings.Builder, cur_m
}
}
fn write_comments(comments []Comment, mut f strings.Builder) {
for i, c in comments {
if !f.last_n(1)[0].is_space() {
f.write_string(' ')
}
write_comment(c, mut f)
if c.is_inline && i < comments.len - 1 && !c.is_multi {
f.write_string(' ')
} else if (!c.is_inline || c.is_multi) && i < comments.len - 1 {
f.writeln('')
}
}
}
fn write_comment(node Comment, mut f strings.Builder) {
if node.is_inline {
x := node.text.trim_left('\x01').trim_space()
if x.contains('\n') {
f.writeln('/*')
f.writeln(x)
f.write_string('*/')
} else {
f.write_string('/* ${x} */')
}
} else {
mut s := node.text.trim_left('\x01').trim_right(' ')
mut out_s := '//'
if s != '' {
if s[0].is_letter() || s[0].is_digit() {
out_s += ' '
}
out_s += s
}
f.writeln(out_s)
}
}
struct StringifyModReplacement {
mod string
alias string
weight int
}
pub fn shorten_full_name_based_on_aliases(input string, m2a map[string]string) string {
fn shorten_full_name_based_on_aliases(input string, m2a map[string]string) string {
if m2a.len == 0 || -1 == input.index_u8(`.`) {
// a simple typename, like `string` or `[]bool`; no module aliasings apply,
// (or there just are not any mappings)

View File

@ -1019,7 +1019,7 @@ pub fn (mut f Fmt) enum_decl(node ast.EnumDecl) {
pub fn (mut f Fmt) fn_decl(node ast.FnDecl) {
f.attrs(node.attrs)
f.fn_header(node)
f.write(f.table.stringify_fn_decl(&node, f.cur_mod, f.mod2alias))
// Handle trailing comments after fn header declarations
if node.no_body && node.end_comments.len > 0 {
first_comment := node.end_comments[0]
@ -1043,136 +1043,6 @@ pub fn (mut f Fmt) fn_decl(node ast.FnDecl) {
f.fn_body(node)
}
pub fn (mut f Fmt) fn_header(node ast.FnDecl) {
if node.is_pub {
f.write('pub ')
}
f.write('fn ')
pre_comments := node.comments.filter(it.pos.pos < node.name_pos.pos)
if pre_comments.len > 0 {
f.comments(pre_comments)
f.write(' ')
}
if node.is_method {
f.write('(')
mut styp := util.no_cur_mod(f.table.type_to_code(node.receiver.typ.clear_flag(.shared_f)),
f.cur_mod)
if node.rec_mut {
f.write(node.receiver.typ.share().str() + ' ')
styp = styp[1..] // remove &
}
f.write(node.receiver.name + ' ')
styp = util.no_cur_mod(styp, f.cur_mod)
if node.params[0].is_auto_rec {
styp = styp.trim('&')
}
f.write(styp + ') ')
} else if node.is_static_type_method {
mut styp := util.no_cur_mod(f.table.type_to_code(node.receiver.typ.clear_flag(.shared_f)),
f.cur_mod)
f.write(styp + '.')
}
mut name := if !node.is_method && node.language == .v {
node.name.all_after_last('.')
} else {
node.name
}
if node.is_static_type_method {
name = name.after('__static__')
}
f.write(name)
if name in ['+', '-', '*', '/', '%', '<', '>', '==', '!=', '>=', '<='] {
f.write(' ')
}
mut add_para_types := true
if node.generic_names.len > 0 {
if node.is_method {
sym := f.table.sym(node.params[0].typ)
if sym.info is ast.Struct {
generic_names := sym.info.generic_types.map(f.table.sym(it).name)
if generic_names == node.generic_names {
add_para_types = false
}
}
}
if add_para_types {
f.write('[')
for i, gname in node.generic_names {
is_last := i == node.generic_names.len - 1
f.write(gname)
if !is_last {
f.write(', ')
}
}
f.write(']')
}
}
f.write('(')
for i, arg in node.params {
before_comments := arg.comments.filter(it.pos.pos < arg.pos.pos)
if before_comments.len > 0 {
f.comments(before_comments, level: .indent)
}
// skip receiver
if node.is_method && i == 0 {
continue
}
if arg.is_hidden {
continue
}
is_last_arg := i == node.params.len - 1
is_type_only := arg.name == ''
should_add_type := true
if arg.is_mut {
f.write(arg.typ.share().str() + ' ')
}
f.write(arg.name)
arg_sym := f.table.sym(arg.typ)
if arg_sym.kind == .struct_ && (arg_sym.info as ast.Struct).is_anon {
f.write(' struct {')
struct_ := arg_sym.info as ast.Struct
for field in struct_.fields {
f.write(' ${field.name} ${f.table.type_to_str(field.typ)}')
if field.has_default_expr {
f.write(' = ${field.default_expr}')
}
}
if struct_.fields.len > 0 {
f.write(' ')
}
f.write('}')
} else {
mut s := f.table.type_to_str(arg.typ.clear_flag(.shared_f))
if arg.is_mut {
if s.starts_with('&') && ((!arg_sym.is_number() && arg_sym.kind != .bool)
|| node.language != .v) {
s = s[1..]
}
}
s = util.no_cur_mod(s, f.cur_mod)
s = ast.shorten_full_name_based_on_aliases(s, f.mod2alias)
if should_add_type {
if !is_type_only {
f.write(' ')
}
if node.is_variadic && is_last_arg {
f.write('...')
}
f.write(s)
}
}
if !is_last_arg {
f.write(', ')
}
}
f.write(')')
if node.return_type != ast.void_type {
sreturn_type := util.no_cur_mod(f.table.type_to_str(node.return_type), f.cur_mod)
short_sreturn_type := ast.shorten_full_name_based_on_aliases(sreturn_type, f.mod2alias)
f.write(' ${short_sreturn_type}')
}
}
pub fn (mut f Fmt) anon_fn(node ast.AnonFn) {
f.write(f.table.stringify_anon_decl(&node, f.cur_mod, f.mod2alias)) // `Expr` instead of `ast.Expr` in mod ast
f.fn_body(node.decl)