ReactiveUI-激活时和输出属性

时间:2018-06-23 09:27:37

标签: c# xamarin reactive-programming reactiveui

我正在使用ReactiveUI,并且尝试使用WhenActivated更改所有ViewModels的规则,但是我无法理解如何使其与输出属性一起很好地工作。

模式类似于

this.WhenActivated(
registerDisposable =>
{
    registerDisposable(this.Bind(…));
    registerDisposable(this.WhenAny(…));
    registerDisposable(this.WhenAnyValue(…));
});

,输出属性看起来像

protected readonly ObservableAsPropertyHelper<object> _Obj;
public object Obj => _Obj.Value
_Obj = this.WhenAnyValue(x => x.Something).ToProperty(this, x => x.Obj, out _Obj);

所以我看到的将它们统一的唯一方法是:

class MyClass {

protected readonly ObservableAsPropertyHelper<object> _Obj;
public object Obj => _Obj.Value

public MyClass()
{
    _Obj = this.WhenAnyValue(x => x.Something).ToProperty(this, x => x.Obj, out _Obj);

    this.WhenActivated( registerDisposable =>
    {
        registerDisposable(_Obj);
    });
}

}

这项工作会按预期进行,还是还有另一种更好的方法?

1 个答案:

答案 0 :(得分:0)

在这种情况下,不需要处理_Obj,因为其他具有与_Obj相同的作用域(它们都包含在MyClass中)。但是,如果要基于服务中包含的可观察对象(通常具有比视图模型更长的生命周期)建立_Obj的基础,那么您就需要对其进行处理。

// _Obj should be disposed of, in this case.
_Obj = someService
    .SomePipeline
    .ToProperty(this, x => x.Obj)

侧面说明:如果要分配值,则无需使用out参数。以下等同于以上内容:

someService
    .SomePipeline
    .ToProperty(this, x => x.Obj, out _Obj)

因此,对于someService,您可以 将_Obj放在WhenActivated中,但可以

  

创建粘性竞态条件,因此OAPH可能为null   相应的属性(Obj)的访问时间过早。

此信息以及上面的引文直接取自肯特·布加特(Kent Boogaart)的书"You, I, and ReactiveUI."

他很友善地为上述情况提供了解决方案,将激活变成了管道。您可以使用these extensions(第一个用于视图模型,第二个用于视图):

_Obj = this
    .GetIsActivated()
    .Select(isActivated => isActivated ? someService.SomePipeline : Observable.Return(null))
    .Switch()
    .ToProperty(this, x => x.Obj);