2009-10-20 121 views
11

将列表传递给Tcl过程的规范方法是什么?将列表传递给Tcl过程

我真的很喜欢它,如果我能得到它,以便一个列表自动扩展到可变数量的参数。

这样类似:

set a {b c} 
myprocedure option1 option2 $a 

myprocedure option1 option2 b c 

是等价的。

我确信我之前看到过这个,但是我无法在网上找到它。任何帮助(和代码),使两个案件相当,将不胜感激。

这是否被认为是标准的Tcl惯例。或者我甚至会吠叫错误的树?

+0

在最好的问题的某个地方添加“unwrap”这个词(最好在“unwrap arguments”中)?我很难找到它:-) – cfi 2012-03-07 22:32:27

回答

14

这取决于中Tcl的版本,您正在使用,但: 8.5:

set mylist {a b c} 
myprocedure option1 option2 {*}$mylist 

8.4及以下:

set mylist {a b c} 
eval myprocedure option1 option2 $mylist 
# or, if option1 and 2 are variables 
eval myprocedure [list $option1] [list $option2] $mylist 
# or, as Bryan prefers 
eval myprocedure \$option1 \$option2 $mylist 
+1

...虽然我个人发现\ $ option1 \ $ option2比[list $ option1] [list $ optio2]更可取。它更接近地表明意图 - 您的意图不是创建一个元素列表,您的意图是防止(或防止)这些变量的额外一轮替代。 – 2009-10-20 20:27:27

+0

对于8.4和以下版本,执行此操作的规范方法是:'eval [linsert $ mylist 0 myprocedure options1 option2]' – 2009-10-21 00:29:09

+2

我不同意这是规范的(但也许我们有不同的规则?)。这可以说是最安全的,但它的可读性比\ $ option1 \ $ option2的可读性要差,并且有点模糊了您实际尝试完成的内容。 – 2009-10-21 02:56:52

0

要扩大RHSeeger的答案,你会编写我的过程与特殊args这样的说法:

proc myprocedure {opt1 opt2 args} { 
    puts "opt1=$opt1" 
    puts "opt2=$opt2" 
    puts "args=[list $args]" ;# just use [list] for output formatting 
    puts "args has [llength $args] elements" 
} 
+0

我不同意你必须编写myprocedure来获取可变数目的参数(即使用“args”)。不管你是这样做的,完全取决于你是否需要输入可变数量的输入,而不是取决于一个特定的调用者是如何使输入可用的。 – RHSeeger 2009-10-21 03:08:48

0

这可能是有用的注意,通过您的命令catch也将解决这个问题:

set a {b c} 
if [catch "myprocedure option1 option2 $a"] { 
    # handle errors 
} 

这也许应该,如果你想在这一点上,以处理myprocedure错误在你的代码,这样你不仅可以使用不必担心重新抛出任何被发现的错误。