这有点类似于这个问题TclOO Variable Scope with Inheritance/superclass, 但我想为我的类中的方法提供一些变量,以及哪些变量在运行时动态确定。 伪代码:
oo::class create myClass {
constructor {registryObject} {
foreach variable [$registryObject getVariables] {
<make $variable visible to all methods>
}
method useVariable{} {
<do something with previously declared variable>
}
}
有没有办法实现这个没有另一层间接?问题是registryObject给了我一些可变数量的对其他对象的引用,我希望在派生类中可以访问它们。与上面引用的问题一样,这里的要点是派生类的代码简洁。如果需要的话,我愿意在超类中使用肮脏而复杂的黑客。
答案 0 :(得分:0)
真的很难完全按照你的要求去做。
TclOO中使用的variable
类声明调整Tcl如何解析在同一个类中声明的(正常类定义的)方法中的变量。它不会影响超类,子类或实例定义的方法(如果需要,它们应该使用自己的variable
声明)。变量本身是虽然可见 - 与实例关联的所有变量都是当前命名空间中的变量,而对象正在执行(这是特定于实例的) - 它们只需要显式引入。
如果使用对注册表对象查询的响应来动态创建实例方法,则可以这样做:
constructor {registryObject} {
foreach variable [$registryObject getVariables] {
oo::objdefine [self] variable $variable
}
oo::objdefine [self] method foo {...} {
# This method *will* have automatic access
}
}
是的,该方法是在构造函数内创建的(并且在类上创建方法没有多大意义)。不,大多数其他对象系统都没有实例方法。可以认为它有点像为每个实例提供自己特殊的小类。 (那不是发生了什么,但它并不太遥远。)
如果你要为类的所有实例创建方法,那么在创建类(无聊,常规!)或创建类的第一个实例期间这样做是有意义的,假设注册表做了明智的事情,并为该类的所有实例提供相同的答案。如果是这样的话,你就可以做到。覆盖create
和new
方法可能是最简单的方法:
oo::class create myClass {
self method create {name registryObject} {
foreach var [$registryObject getVariables] {
oo::define [self] variable $var
}
next $name $registryObject
}
self method new {registryObject} {
foreach var [$registryObject getVariables] {
oo::define [self] variable $var
}
next $registryObject
}
constructor ...
method ...
}
这样做有点慢,因为每个对象创建都会触发重新编译很多东西,但它应该有用。
或者你可以在构造函数中执行它;我认为它不那么优雅,但你可能不同意:
constructor {registryObject} {
oo::define [self class] variable {*}[$registryObject getVariables]
}
我认为这两个选项都不是很好的方法 ,我建议在创建类时进行注册表查找。或者使方法不依赖于variable
机制,而是使用my variable
(非常类似于global
但是例如变量)来访问他们需要的变量。
如果我能更准确地弄清楚大局是什么,我可以帮助你更好......