目录
脚本、命令和单词符
置换
变量置换
命令置换
反斜杠置换
双引号和花括号
注释
一个 TCL 脚本可以包含一个或多个命令。命令之间必须用换行符或分号隔开。
set a 1
set b 2
或者
set a 1;set b 2 都是合法的
TCL 的每一个命令包含一个或几个单词,第一个单词代表命令名,另外的单词则是这个命令的参数,单词之间必须用空格或 TAB 键隔开。
TCL 解释器对一个命令的求值过程分为两部分:分析和执行。在分析阶段,TCL 解释器运用规 则把命令分成一个个独立的单词,同时进行必要的置换(substitution); 在执行阶段,TCL 解 释器会把第一个单词当作命令名,并查看这个命令是否有定义,如果有定义就激活这个命令对应 的 C/C++过程,并把所有的单词作为参数传递给该命令过程,让命令过程进行处理。
TCL 解释器在分析命令时,把所有的命令参数都当作字符串看待
set x 10 //定义变量 x,并把 x 的值赋为 10
set y x+100 //y 的值是 x+100,而不是我们期望的 110
x 被看作字符串 x+100 的一部分,如果我们想使用 x 的值'10' ,就必 须告诉 TCL 解释器:我们在这里期望的是变量 x 的值,而非字符'x'。怎么告诉 TCL 解释器呢, 这就要用到 TCL 语言中提供的置换功能。
TCL 提供三种形式的置换:变量置换、命令置换和反斜杠置换。每种置换都会导致一个或多个单词本身被其他的值所代替。置换可以发生在包括命令名在内的每一个单词中,而且置换可以嵌套。
变量置换由一个$符号标记,变量置换会导致变量的值插入一个单词中。
set y $x+100 //y 的值是 10+100,这里 x 被置换成它的值 10
这时,y 的值还不是我们想要的值 110,而是 10+100,因为 TCL 解释器把 10+100 看成是 一个字符串而不是表达式,y 要想得到值 110,还必须用命令置换,使得 TCL 会把 10+100 看 成一个表达式并求值。
命令置换是由[]括起来的 TCL 命令及其参数,命令置换会导致某一个命令的所有或部分单词被另一个命令的结果所代替。
set y [expr $x+100] //输出结果y是110
这里当 TCL 解释器遇到字符'['时,它就会把随后的 expr 作为一个命令名,从而激活与 expr 对应的 C/C++过程,并把'expr'和变量置换后得到的'10+110'传递给该命令过程进行处理。 如果在上例中我们去掉[],那么 TCL 会报错。因为在正常情况下,TCL 解释器只把命令行中的第一个单词作为看作命令,其他的单词都作为普通字符串处理,看作是命令的参数。
注意,[]中必须是一个合法的 TCL 脚本,长度不限。[]中脚本的值为最后一个命令的返回值。
set y [expr $x+100;set b 300] //y 的值为 300,因为 set b 300 的返回值为 300
有了命令置换,实际上就表示命令之间是可以嵌套的,即一个命令的结果可以作为别的命令的参 数。
TCL 语言中的反斜杠置换类似于 C 语言中反斜杠的用法,主要用于在单词符号中插入诸如换行 符、空格、[、$等被 TCL 解释器当作特殊符号对待的字符。
set msg multiple\ space //msg 的值为 multiple space。
如果没有'\'的话,TCL 会报错,因为解释器会把这里最后两个单词之间的空格认为是分隔符, 于是发现 set 命令有多于两个参数,从而报错。加入了'\'后,空格不被当作分隔符,'multiple space'被认为是一个单词(word)。
set msg money\ \$3333\ \nArray\ a\[2] //这个命令的执行结果为:
money $3333
Array a[2]
例子:
set a \x48 //对应 \xhh
H //十六进制的 48 正好是 72,对应 H
set a \110 //对应 \ddd
H //八进制的 110 正好是 72,对应 H
set a [expr \ // 对应\newline space,一个命令可以用\newline 转到下一行继续
2+3]
5
除了使用反斜杠外,TCL 提供另外两种方法来使得解释器把分隔符和置换符等特殊字符当作普通字符,而不作特殊处理,这就要使用双引号和花括号({})。
TCL 解释器对双引号(“”)中的各种分隔符将不作处理,但是对换行符/ 及$和[]两种置换符会照常处理。
set x 100
100
set y "$x ddd"
100 ddd
而在花括号中,所有特殊字符都将成为普通字符,失去其特殊意义,TCL 解释器不会对其作特 殊处理。
set y {/n$x [expr 10+100]}
/n$x [expr 10+100]
TCL 中的注释符是'#','#'和直到所在行结尾的所有字符都被 TCL 看作注释,TCL 解释器对注 释将不作任何处理。不过,要注意的是,'#'必须出现在 TCL 解释器期望命令的第一个字符出现 的地方,才被当作注释。 例如:
#This is a comment
set a 100 # Not a comment
输出:wrong # args: should be "set varName ?newValue?"
set b 101 ; # this is a comment
输出:101
第二行中'#'就不被当作注释符,因为它出现在命令的中间,TCL 解释器把它和后面的字符当作 命令的参数处理,从而导致错误。而第四行的'#'就被作为注释,因为前一个命令已经用一个分 号结束,TCL 解释器期望下一个命令接着出现。现在在这个位置出现'#',随后的字符就被当作注释了。