【问题标题】:Reactive Extensions for .NET (Rx): Take action once all events are completed.NET (Rx) 的反应式扩展:在所有事件完成后采取行动
【发布时间】:2010-10-05 21:24:38
【问题描述】:

作为概念证明,我想在文本框中写“完成” 选中复选框并在文本框中按下一个键(以任意顺序)。我希望这段代码能够处理这个问题,但只要任何一个事件发生,它就会写完成。感谢您的帮助。

var seq = Observable.FromEvent<EventArgs>(this.checkBox, "CheckedChanged")
   .Merge(Observable.FromEvent<KeyPressEventArgs>(this.textBox, "KeyPress"));

seq.Subscribe((unused) => this.resultTextBox.Text = "Done");

【问题讨论】:

    标签: c# .net system.reactive


    【解决方案1】:

    你可以使用 Observable.When 像这样(我为此示例添加了一个额外的 CheckBox):

    var checkChanged  = Observable.FromEvent<EventArgs>(this.checkBox, "CheckedChanged");
    var check1Changed = Observable.FromEvent<EventArgs>(this.checkBox1, "CheckedChanged");
    var keyPress      = Observable.FromEvent<KeyPressEventArgs>(this.textBox, "KeyPress");
    
    var plan1 = checkChanged
                .And(check1Changed).And(keyPress)
                .Then((cc, cc1, kp) => "Done.");
    
    var when = Observable.When(plan1);
    
    when.Subscribe((result) => this.resultTextBox.Text = result);
    

    此外,如果您可以将其他计划一起加入,例如,当一组事件触发或另一组事件触发时,事情是否可以“完成”:

    var checkChanged  = Observable.FromEvent<EventArgs>(this.checkBox, "CheckedChanged");
    var check1Changed = Observable.FromEvent<EventArgs>(this.checkBox1, "CheckedChanged");
    var keyPress      = Observable.FromEvent<KeyPressEventArgs>(this.textBox, "KeyPress");
    var keyPress1     = Observable.FromEvent<KeyPressEventArgs>(this.textBox1, "KeyPress");
    
    var plan1 = checkChanged.And(check1Changed).And(keyPress).Then((cc, cc1, kp) => "Done.");
    var plan2 = keyPress.And(keyPress1).Then((kp, kp1) => "Alternate done.");
    
    var join = Observable.When(plan1, plan2);
    

    【讨论】:

    • 谢谢 - 我也玩过这种方法。如果这些事件是异步的。网络调用,你更喜欢这种风格而不是 Zip 方法吗?
    • 我喜欢这样。在其中一个事件中处理错误情况是一件小事吗?
    • 我还没试过用 Zip 做这个,顺便说一句。也许我稍后会尝试比较。
    • 通过采用 OnError 操作的订阅重载处理错误。例如:join.Subscribe((result) => this.resultTextBox.Text = result, ex => Console.WriteLine("Error: {0}", ex.Message));
    【解决方案2】:

    如果您需要同时发生这两个事件 - 请考虑使用 Zip。如果 任何 合并源引发事件,合并将触发该事件。

    【讨论】:

    • 如果有 10 个不同的事件,而不是两个呢?
    • Zip 返回 Observable,当两个来源都引发它时(如会合),它将触发事件。您可以将此结果 Observable 与另一个压缩,以获得连接到 3 个源等的 Observable...
    • 这是一个合理的方法吗?将 Observable.Join 与 Ands 一起使用怎么样?
    猜你喜欢
    • 1970-01-01
    • 2011-09-25
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多