【问题标题】:What is the use case for cold observables?冷可观察对象的用例是什么?
【发布时间】:2016-05-01 15:29:31
【问题描述】:

我了解热可观察对象和冷可观察对象之间的区别,但我总是看到人们使用热可观察对象而不是冷对象;事实上,如果有人不小心使用了一个冷的 observable,它就会被认为是一个错误,因为这通常是导致不良行为的原因。

在什么情况下您更喜欢或使用冷的 observable 而不是热的?

【问题讨论】:

  • 目的是不使用时冷。你可以创建 observable,不管它是否被使用,但它不会占用任何资源。
  • @Bergi 那么有什么优势呢?懒惰?

标签: javascript rxjs observable


【解决方案1】:

首先,我邀请您查看Hot and Cold observables : are there 'hot' and 'cold' operators?,以确保您对热与冷有一个透彻的了解。

Cold observables 允许生产者的懒惰,这是一个非常理想的特性。当没有使用这些价值(没有消费者)时,产生价值(生产可能很昂贵)是一种浪费。因此,冷的可观察对象是构建块......更经常地从中派生出热的可观察对象。

因此,冷 observables 最常见的用例是懒惰地导出 hot observables。如果您考虑一下,您需要以某种方式以编程方式构建这些热门的可观察对象。一种方法是使用主题(您就是制作人)。另一种方法是通过运算符从其他预先存在的 observables 派生它们,预先存在的 observables 也是从其他人派生的等等。在链的末端,你应该找到Rx.Observable.create,这是一个冷的 observable。

当您需要惰性时,您使用冷可观察(仅在有消费者时才开始产生值,或控制生产过程的开始)。例如,defer 允许您仅在有消费者时启动生产者。例如,当您有一个 hot observable 但您还没有准备好收听它时,可以使用它。

当您需要重现一个产生价值的过程时,您还需要冷的 observables(每个新订阅者都将重新启动完全相同的过程)。例如,出于测试目的,您想多次使用完全相同的序列,但在不同的消费者和不同的时间使用。

最后,这个问题听起来更像是一个哲学问题。您可以使用两种工具,重要的是了解您需要什么、您拥有什么以及哪些适合您的用例。

【讨论】:

    【解决方案2】:

    答案的核心在于 Ben Lesh 的简洁总结:

    TL;DR:当你不想创建你的 制作人一遍又一遍。

    在直接回答“在什么情况下,您更喜欢或使用冷可观察对象而不是热可观察对象?”时,我将提供一般性答案和具体示例。

    通常,使用冷的 observable 对每次需要它们时创建的流进行建模要比创建一个热的流并尝试对其进行处理要方便得多。

    具体来说,考虑以下简单的示例。假设您想通过从 10 倒计时来响应单击按钮。如果在倒计时期间再次单击该按钮,它会再次从 10 开始。如果 click$ 为按钮事件建模,您可能会遇到这样的情况:

    const subscription = click$
      .flatMapLatest(_ => Rx.Observable.interval(1000).take(10))
      .select(x => 10 - x)
      .subscribe(x => console.log('clicked: ' + x));
    

    考虑如何在没有冷观测值的情况下对其进行建模。你会怎么做:

    1. 提前初始化流,以便在需要时提供适当的值?
    2. 避免处理间隔滴答和订阅时间之间的几分之一秒?
    3. 处理可以从任何数字而不是 1 开始的序数?
    4. 管理流的清理逻辑?

    1 和 3 可以很容易地解决,但 2 和 4 很糟糕。

    回答你的第二个问题“是懒惰吗?”我认为它不是。一个冷的 observable 可以让它直到订阅的那一刻才产生它的值。一个热的 observable 可以将其保留到订阅的那一刻以挂钩适当的事件。他们都以自己的方式懒惰(或者至少可以)。关键区别在于 Ben Lesh 所说的:你想每次都创建一个制片人吗?有时,你真的会这样做。

    【讨论】:

      【解决方案3】:

      在什么情况下您更喜欢或使用冷的 observable 而不是热的?

      我希望我不是在陈述显而易见的事情,而是在任何情况下,您想要从 observable 的历史记录中访问 所有 值(或通过过滤完整集获得的某个子集)。

      想到的第一个例子是平均所有学生的考试成绩,而不仅仅是订阅后的成绩。

      【讨论】:

      • 嗯,有道理。你能概括一下你的答案吗?还有其他情况吗?他们都有什么共同点?最后,为什么热流做不到这些?
      • @ar7 据我了解,我认为任何涉及 observable 完整历史(或通过过滤整个集合得到的某个子集)的场景都需要冷 observable。此外,this 的回答和链接的博客文章触及了您关于懒惰的问题。
      • @ar7 另外,我发现 RxJS 文档的 the Analogies section 很有启发性。
      • 我实际上已经看到了这一点,这实际上是激发我的问题的一部分。它创造了类比,这很有意义,但对我来说还不够全面。另外,如果您可以播放热门的可观察对象,为什么还要“电影”?有什么区别?
      • @ar7 关于播放的问题很有趣,不幸的是,我没有给你一个好的答案。有趣的是,this 的回答暗示了将热的 observable 转换为冷的 observable 的操作。
      猜你喜欢
      • 1970-01-01
      • 2017-09-26
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2023-03-06
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多