我开始了解Haxe,我主要使用它来生成Python代码和C#DLL。
但是我多次遇到同样的问题:每当我尝试编写getter时,当我从方法内部访问相关属性时它们工作正常,但是当我尝试从类外部访问它们时,它们甚至都没有被调用。我开始怀疑我错过了一些基本的东西。
例如,如果我写下面的类:
@:expose
@:keep
class TestClass
{
public var testField(get, null):String;
private function get_testField():String
{
trace("executing getter");
return "testString";
}
public function new() {}
public function testMethod()
{
trace(testField);
}
}
然后在Python中:
testInstance = MyModule.TestClass();
testInstance.testMethod();
......按预期输出:
executing getter
testString
但
print(testInstance.testField)
...输出None
。
我期待testInstance.testField
在任何情况下都会返回"testString"
,我做错了什么?这也发生在C#中。
这是因为properties in Haxe are a compile-time feature并没有生成本机属性。并非所有目标都具有属性,而那些可能不会与Haxe的语义完全匹配的目标。
相反,在编译时调用访问器方法(get_field()
,set_field()
)会替换属性访问。所以,
trace(testField);
编译为Python时变为以下内容:
print(str(self.get_testField()))
因此,要获得一致的结果,您还必须在Python端调用get_testField()
。
对于C#和Flash目标,有生成本机属性的元数据(请参阅haxe --help-metas
):
@:property
- 标记要编译为本机C#属性的属性字段(仅限cs)
@:getter
- (类字段名称)在给定字段上生成本机getter函数(仅限flash)
@:setter
- (类字段名称)在给定字段上生成本机setter函数(仅限flash)
请注意,C#目标的@:property
仅适用于没有physical field的属性。在你的例子中,(get, null)
必须用(get, never)
替换它才能工作。
目前有一个open feature request用于通过@:property
支持JS目标上的本机属性。这也可能对Python有意义,因为它也具有原生属性。也许考虑开一个问题。 :)