TCL 中的 global 和 :: 有什么区别? [英] What is the difference between global and :: in TCL?
问题描述
我正在使用 EDA SW.它需要我依赖全局变量.假设我有一个 proc,我正在寻找一个全局变量 CCK_FOO.我有两个选择:
I am working with an EDA SW. It requires me to rely on global variables. Say I have a proc, and I am looking for a global variable CCK_FOO. I have 2 choices:
- 在代码中使用
global CCK_FOO
. - 使用
::CCK_FOO
就管理级别"而言,这些似乎相同.这两种方法是否有幕后"的优缺点?我实际上更喜欢使用 ::
,因为它最大限度地减少了意外覆盖的机会.
In terms of "management level", these appear identical. Is there an "under the hood" pro and con for either of the methods? I actually prefer using ::
, as it minimizes the chances of accidental override.
推荐答案
在幕后,使用 ::CCK_FOO
每次执行引擎使用它时都会经过解析的变量名路由,而 global CCK_FOO
允许引擎设置链接到全局变量的局部变量(带有局部变量表——LVT——槽).通过 LVT 访问要快得多,因为这只是一个 C 数组的索引(还有一个额外的指针取消引用,因为它是一个链接)而查找全局变量意味着进行哈希表查找(全局命名空间中有一个变量的哈希表)执行).::CCK_FOO
的实际内部解析为 ::
和 CCK_FOO
被缓存.
Under the hood, using ::CCK_FOO
goes through the parsed variable name route every time the execution engine uses it, whereas global CCK_FOO
allows the engine to set up a local variable (with a local variable table — LVT — slot) that is linked to the global variable. Accesses via the LVT is much faster because that's just an index into a C array (and an extra pointer dereference because it's a link) whereas looking up a global variable means doing a hash table lookup (there's a hash table for variables in the global namespace implementation). The actual internal parse of ::CCK_FOO
into ::
and CCK_FOO
is cached.
实际上,如果您只访问一个变量一次,则使用 ::CCK_FOO
可能稍微更快,但是一旦您使用它两次(更不用说更多)您可以通过支付 global CCK_FOO
的额外成本并通过 LVT 索引访问它来获得更好的性能.
In practical terms, it's perhaps slightly faster to use ::CCK_FOO
if you are only accessing a variable once, but as soon as you use it twice (let alone more) you get better performance by paying the extra cost of global CCK_FOO
and accessing it via LVT indexing.
% proc style1 {} {
set ::CCK_FOO abc
}
% proc style2 {} {
global CCK_FOO
set CCK_FOO abc
}
% time { style1 } 100000
0.52350635 microseconds per iteration
% time { style2 } 100000
0.5267007100000001 microseconds per iteration
请注意,上面的代码和下面的代码之间的时间没有可比性,因为它们做了不同数量的其他工作.而是查看 style1
和 style2
之间的时间差异.
Note, times between code above and code below are not comparable as they do different amounts of other work. Look instead at the differences in timings between style1
and style2
.
% proc style1 {} {
set ::CCK_FOO [string reverse $::CCK_FOO]
}
% proc style2 {} {
global CCK_FOO
set CCK_FOO [string reverse $CCK_FOO]
}
% time { style1 } 100000
0.9733970200000001 microseconds per iteration
% time { style2 } 100000
0.78782093 microseconds per iteration
# Calibration...
% time { string reverse abc } 100000
0.28694849 microseconds per iteration
如您所见,只需两次访问,我们通过使用 global
获得了相当多的加速.
As you can see, with just two accesses, we're getting quite a lot of speedup by using global
.
这篇关于TCL 中的 global 和 :: 有什么区别?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!