将全局变量传递给 tclsh 中的函数

时间:2021-05-08 09:33:27

标签: tcl

我首先为字符串定义了 3 个(全局)常量:

set kColorGBegin "\x1b\[1;32m"
set kColorRBegin "\x1b\[1;31m"
set ColorEnd  "\x1b\[0m"

然后我创建了 2 个渲染和打印输入字符串的函数:

proc r_puts {strs} {
  puts "${kColorRBegin} ${strs} ${ColorEnd}"
}
proc g_puts {strs} {
  puts "${kColorGBegin} ${strs} ${ColorEnd}"
}

并调用:

[r_puts "foo"]
[g_puts "bar"]

我在运行这个程序时收到错误信息:

can't read "kColorRBegin": no such variable
    while executing
"puts "${kColorRBegin} ${strs} ${ColorEnd}""
    (procedure "r_puts" line 2)
    invoked from within
"r_puts "foo""
    invoked from within
"[r_puts "foo"]"
    (file "./t.tcl" line 14)

我该如何解决?


完整代码在这里:

set kColorGBegin "\x1b\[1;32m"
set kColorRBegin "\x1b\[1;31m"
set ColorEnd  "\x1b\[0m"

proc g_puts {strs} {
  puts "${kColorGBegin} ${strs} ${ColorEnd}"
}

proc r_puts {strs} {
  puts "${kColorRBegin} ${strs} ${ColorEnd}"
}

[r_puts "foo"]
[g_puts "bar"]

2 个答案:

答案 0 :(得分:1)

在 Tcl 中,过程中的所有变量都是过程的局部变量除非您在该过程中另有说明;从长远来看,必须明确说明这一点可以避免各种麻烦。 (对象方法中的事情稍微复杂一些,但您并没有处理这些,即使这样,当您明确要求它时它们才会变得复杂。)这通常在过程中使用 the global command 完成,例如这个:

proc r_puts {strs} {
    global kColorRBegin ColorEnd
    puts "${kColorRBegin} ${strs} ${ColorEnd}"
}
proc g_puts {strs} {
    global kColorGBegin ColorEnd
    puts "${kColorGBegin} ${strs} ${ColorEnd}"
}

您可能希望省略变量替换之间的空格。


用于此的其他命令是:variable(通常在处理全局命名空间以外的命名空间中的少量变量时)、upvar(当处理从名称传递的变量时caller) 和 namespace upvar(当在一个命名空间而不是全局命名空间中处理许多变量时)。

答案 1 :(得分:1)

不要在对 r_puts 和 g_puts 的调用周围放置大括号:这将调用 procs 作为命令替换,用结果替换命令替换,然后尝试将结果作为命令执行

演示:

$ tclsh
% proc r_puts {msg} {puts $msg}
% r_puts hello
hello
% [r_puts hello]
hello
ambiguous command name "": after append apply ...
相关问题