Vala 闭包引用循环
Vala closure reference cycle
我正在 Vala 中编写一个 class,其中我 bind 将同一对象的两个属性放在一起,并使用闭包将一个转换为另一个。
class Foo : Object
{
public int num { get; set; }
public int scale = 2;
public int result { get; set; }
construct {
this.bind_property("num", this, "result", 0,
(binding, src, ref dst) => {
var a = src.get_int();
var b = this.scale;
var c = a * b;
dst.set_int(c);
}
);
}
}
闭包保留了一个引用 this
(因为我使用了 this.scale
),它创建了一个引用循环,它使我的 class 保持活动状态,即使对它的所有其他引用都丢失了.
只有当引用计数达到 0 时,绑定才会被删除,但只有当投标及其关闭被删除时,refcount 才会达到 0。
有没有办法使闭包对 this
的引用变弱?或者探测引用计数何时达到 1 以将其删除?
未测试,但您可以将 this
分配给弱变量并在闭包中引用它吗?例如:
weak Foo weak_this = this;
this.bind_property(…, (…) => {
…
b = weak_this.scale;
…
}
这是 Vala 编译器的一个已知缺陷,在 this issue 中进行了讨论。
目前,可以通过从闭包不捕获的静态方法进行绑定来避免该问题 this
。
class Foo : Object
{
public int num { get; set; }
public int scale = 2;
public int result { get; set; }
construct {
this.bind_properties(this);
}
private static void bind_properties(Foo this_)
{
weak Foo weak_this = this_;
this_.bind_property("num", this_, "result", 0,
(binding, src, ref dst) => {
var a = src.get_int();
var b = weak_this.scale;
var c = a * b;
dst.set_int(c);
}
);
}
}
我正在 Vala 中编写一个 class,其中我 bind 将同一对象的两个属性放在一起,并使用闭包将一个转换为另一个。
class Foo : Object
{
public int num { get; set; }
public int scale = 2;
public int result { get; set; }
construct {
this.bind_property("num", this, "result", 0,
(binding, src, ref dst) => {
var a = src.get_int();
var b = this.scale;
var c = a * b;
dst.set_int(c);
}
);
}
}
闭包保留了一个引用 this
(因为我使用了 this.scale
),它创建了一个引用循环,它使我的 class 保持活动状态,即使对它的所有其他引用都丢失了.
只有当引用计数达到 0 时,绑定才会被删除,但只有当投标及其关闭被删除时,refcount 才会达到 0。
有没有办法使闭包对 this
的引用变弱?或者探测引用计数何时达到 1 以将其删除?
未测试,但您可以将 this
分配给弱变量并在闭包中引用它吗?例如:
weak Foo weak_this = this;
this.bind_property(…, (…) => {
…
b = weak_this.scale;
…
}
这是 Vala 编译器的一个已知缺陷,在 this issue 中进行了讨论。
目前,可以通过从闭包不捕获的静态方法进行绑定来避免该问题 this
。
class Foo : Object
{
public int num { get; set; }
public int scale = 2;
public int result { get; set; }
construct {
this.bind_properties(this);
}
private static void bind_properties(Foo this_)
{
weak Foo weak_this = this_;
this_.bind_property("num", this_, "result", 0,
(binding, src, ref dst) => {
var a = src.get_int();
var b = weak_this.scale;
var c = a * b;
dst.set_int(c);
}
);
}
}