您好,欢迎访问三七文档
TCL编程高级教程测试平台开发部周健明04245培训内容•命名空间•脚本库和程序包•ITCL命名空间•命名空间的基本概念命名空间概念定义命名空间示例限定命名名称解析输入命令输出命令命名空间的命令参考命名空间•命名空间的基本概念命名空间是一个命令与变量的集合。命名空间把命令和变量封装起来以确保它们不会干扰别的命名空间中的命令和变量。TCL已经有一个这样的集合,就是我们指的全局命名空间。全局命名空间将所有的全局变量和命令放在一起。命名空间也叫做名称空间、名称域、命名域等。命名空间•命名空间创建:用namespaceeval命令创建一个新的命名空间•命名空间查询如果要在命名空间XXX之外查询命名空间内部变量的值xxx,可以用如下语句:set::XXX::xxx命名空间•命名空间示例1:用namespaceeval命令创建一个新的命名空间:namespaceevalCounter{namespaceexportbumpvariablenum0procbump{}{variablenumincrnum}}set::Counter::num::Counter::bump命名空间•命名空间示例2:命名空间是动态的。你可以在任何时候添加、删除命令和变量:namespaceevalCounter{variablenum0procbump{}{variablenumreturn[incrnum]}}命名空间•命名空间示例2:命名空间是动态的。你可以在任何时候添加、删除命令和变量:namespaceevalCounter{proctest{args}{return$args}}namespaceevalCounter{renametest}test过程先被加到Counter命名空间中,稍后又被rename命令移除了命名空间•命名空间示例3:命名空间里面可以拥有其它的命名空间形成一个嵌套的分层目录结构。namespaceevalFoo{variablefooVar0......namespaceevalCounter{namespaceexportbumpvariablenum0procbump{}{variablenumincrnum}}}命名空间•命名空间示例3:现在如果在Foo之外访问num就要把Foo也加入到限定命名中:•set::Foo::Counter::num而在Foo内部访问num就只需要用:•setCounter::numset::Foo::Counter::num命名空间•限定命名限定命名又叫限定名称、资格命名或资格名称,英文原名为qualifiednames每一个命名空间有一个原始的名称诸如histroy或::safe::interp。由于命名空间可能嵌套,限定命名被用来表示命令、变量、子命名空间。限定命名跟Unix的路径或TK部件(widgets)的分层目录结构类似,只是命名空间的限定命名使用::作为分隔符而不是/或.而已。最顶层或全局的命名空间的名称是空(如:空字符串),在形式上与::同义。如果你想访问另一个命名空间中的命令和变量,你必须使用额外的语法结构,使用命名空间的限定命名。命名空间•限定命名•除了全局命名空间外,命名空间的命名都不为空。•除了作为命名空间的分隔符外,::也不被简单的命令、变量、命名空间命名接受。•在限定命名尾部的::表示该命名空间变量或命令的命名是{},因此在限定命名空间名称尾部的::会被忽略。另外,在限定命名中单个的:将被看作单个的字符,而2个或更多的单个:将被当作一个命名空间分隔符看待。•例如:namespaceeval::aa::bb::cc{setx100};#定义命名空间::aa::bb::cc中的变量xset::aa::bb::cc::x;#查询x的值,将返回100set::aa:::bb::::cc::::x;#也返回100,b与c之间的3个:,c与x之间的4个:都被当作一个::看待set::aa:bb::c::x;#将出错,因为b与c之间的1个:被当作普通的字符看待,但并没有定义::a:bb这样的命名空间,所以要小心!::aa::bb表示的是命名空间aa下的命名空间bb,而::aa:bb表示的是命名空间aa:bb。命名空间•名称解析一般来说,所有的TCL命令都支持变量和命令的限定命名。也就是说你可以在set、proc、rename、interpalias等命令中使用限定命名。如果你提供以::开头的完整限定命名,则可以精确地找到你指的命令、变量或命名空间。命名空间•名称解析如果命名不是以::开头的,则意味着相对路径的命名,TCL提供如下的名称解析策略:首先在当前命名空间中查找,如果没有才在全局命名空间查找。如果在当前命名空间和全局命名空间都没找到,则该命名尚未定义。例1:settraceLevel0namespaceevalDebug{printTrace$traceLevel}TCL首先在命名空间Debug中查找traceLevel,然后是全局命名空间。命名空间•名称解析例2:settraceLevel0namespaceevalFoo{variabletraceLevel3namespaceevalDebug{printTrace$traceLevel}}TCL首先在命名空间Foo::Debug中查找traceLevel,因为没找到,所以就到全局命名空间中查找。在命名空间Foo中定义的变量Foo::traceLevel既不是当前命名空间Foo::Debug中的变量,也不是全局命名空间中的变量,因此在名称解析的过程中被完全忽略了。命名空间•输入命令和输出命令命名空间常常用来描述库,需要频繁使用命名空间前缀,用输入命令和输出命令可以省略命令前面的命名空间前缀。输入命令:namespaceimport输出命令:namespaceexport命名空间•输入命令namespaceimport命令只输入命名空间中用namespaceexport命令输出的命令如果不再需要使用已经输入的命令,可以使用namespaceforget示例:namespaceimportBlt::graphBlt::table就只输入graph和table命令到当前上下文中。用namespaceforget命令来移除:namespaceforgetBlt::*。当你在输出命名空间中删除一个命令时(如:renameBlt::graph),该命令也自动从所有输入它的命名空间中移除。命名空间•输出命令在命令空间中输出命令,用namespaceexport命令声明要输出的命令:namespaceexportxxxnamespaceexport命令指明了哪些命令可以被其他命名空间输入。namespaceimport命令只输入那些在命名空间中明确定义为输出的命令。如果namespaceimport命令指定了一个没有输出的命令,该命令不会被输入。命名空间•命名空间的命令参考:namespace命令:命令与变量的上下文创建和维护是通过namespace命令来进行的命名空间的创建和删除命名空间的环境抓取和脚本执行命名空间的输入和输出命名空间信息查询限定命名操作命名空间•命名空间的其他相关命令:variable命令:variable命令用于创建和初始化一个命名空间的变量glob-style(glob样式):glob本身是使用通配符查找符合特定pattern的文件名的命令,而glob-style(样式)的就是指使用与glob语法相同的通配符进行模糊查找的匹配方式。培训内容•命名空间•脚本库和程序包•ITCL脚本库和程序包•脚本库什么是脚本库创建和调用脚本库脚本库的优缺点•程序包什么是程序包创建程序包索引文件pkgIndex.tcl使用程序包•与脚本库和程序包相关的全局变量和过程脚本库和程序包•脚本库Q:什么是脚本库?A:TCL中提供了Library来存放一些有用的TCL过程的集合,就是脚本库。使用脚本库的好处是应用程序可以由一个较短的主程序、一个或多个支持库组成,这样应用程序加载时只加载主程序,而支持库中的过程会在使用时才加载,可以缩短整个应用程序的加载时间。脚本库的另一个好处是可以供多个应用程序使用,这样也可以提高程序的共享和复用。另外,脚本库还提供自动加载机制。脚本库和程序包•创建脚本库:STEP:创建脚本库只需以下两步:第一,创建脚本文件。第二步,为自动加载创建索引文件。在TCL解释器(如tclsh或wish)中,执行命令:auto_mkindexpath[patternpattern...]脚本库和程序包•调用脚本库:–在脚本库及其tclIndex文件被创建后,只需要把脚本库的路径添加到TCL的全局变量auto_path中即可,以后就可以自由引用脚本库中的过程。–TCL会自动搜索auto_path每个路径下的tclIndex文件来确定要调用的过程在哪里。一般使用lappend命令将路径添加到auto_path中,例如:%lappendauto_pathc:/tcllib/lib1C:/DEVELOP/TCL/lib/tcl8.3C:/DEVELOP/TCL/libC:/DEVELOP/TCL/lib/tk8.3c:/tcllib/lib1–如果一个函数在几个脚本库中都有定义的话,TCL会按照搜索顺序自动加载在auto_path中位置靠前的那个库。因此,如果加载的脚本库要先被搜索的话,可以使用linsert命令将其插入到auto_path中靠前的位置中,例如:%setauto_path[linsert$auto_path0c:/tcllib/lib1]c:/tcllib/lib1C:/DEVELOP/TCL/lib/tcl8.3C:/DEVELOP/TCL/libC:/DEVELOP/TCL/lib/tk8.3脚本库和程序包•脚本库的优缺点优点:脚本库的方法从TCL的最早版本开始就支持,不存在兼容性问题,很多现有的公共脚本就是使用脚本库创建的。由于通过把路径添加到auto_path变量中来实现对脚本库的定位,因此脚本库可以存放在任何位置,没有路径限制。缺点:不支持版本号,不便于脚本库的更新和维护。由于脚本库只能用TCL语言编写,能够实现的功能有限。另外,每个脚本库的路径都要添加到auto_path变量中也比较烦琐。为解决上述问题和进一步提高TCL的扩展能力,较新版本的TCL提供了更好的程序包机制。脚本库和程序包•程序包Q:什么是程序包?A:由于脚本库的局限性,TCL提供了更好的package机制来实现对TCL的共用和扩展,也就是程序包。脚本库和程序包•创建TCL程序包:把你想包含在某个包中的所有自定义过程放到一个TCL脚本文件中,然后在文件的开头使用packageprovide命令指明这个包的名字和版本即可。脚本库和程序包•创建二进制程序包:–用TCL编写的程序包,功能仍然有限,因此TCL还特别支持二进制程序包。这样,就可以用C/C++语言编写TCL扩展命令了,充分利用Windows或UNIX系统提供的强大API功能。–二进制程序包实际上就是由系统平台所支持的编译后的可执行代码共享库。根据当前系统平台的不同,二进制程序包的文件后缀也不一样。在UNIX上二进制程序包的后缀是.so,在Macintosh上是.shlib,而在Windows上就是我们所熟悉的动态连接库.dll。脚本库和程序包•索引文件pkgIndex.tcl生成索引文件pkgIndex.tcl–自动生成pkgIndex.tcl文件的命令:pkg_mkIndex。–pkg_mkIndex[-lazy][-loadpkgPattern][-verbose]path[patternpattern...]脚本库和程序包•如何使用程序包:–使用某一个程序包时,可以调用packagerequire命令,该命令对TCL和二进制的程序包都适用。–命令格式:
本文标题:TCL编程高级教程
链接地址:https://www.777doc.com/doc-2862138 .html