观察者和订阅者有什么区别?

2022-08-31 11:10:23

我正在尝试破译以下函数:

Subscription getCar(id, Observer<Car> observer) {
    return getCarDetails(id, new Observer<CarDetails> {
                             @Override
                             onNext(CarDetails details) {           
                                 observer.onNext(details.getCar());
                             } });
}

我从 http://blog.danlew.net/2014/09/15/grokking-rxjava-part-1/ 那里得到了一个很好的rxjava介绍,但它只是顺便提到了Observer,说你大部分时间都会使用订阅者来消费从可观察对象发出的物品。

有人可以向我解释吗

  1. 什么是观察者?
  2. 观察者与订阅者有何不同?
  3. 上面的代码片段有什么作用?

Javadoc使它看起来就像一个订阅者。订阅者的javadoc表示它实现了观察者和订阅。我很困惑。


答案 1

已编辑:有@Alrid的评论

tl;博士

public abstract class Subscriber<T> implements Observer<T>, Subscription

因此,订阅者观察者的实现,在订阅上具有其他语义(它更多的是关于取消订阅)。问题中的代码只是表明它传递接口,而不是实现(通常的编程实践)。Observer

此外,此代码返回一个 ,这可能是因为此代码的作者认为客户端应该只能访问方法,而不能访问可观察量生成的元素。这可能是程序员的错误。SubscriptionSubscription

说来话长

真的你应该阅读这个网站(或书)的内容:http://www.introtorx.com 这是关于 Rx.Net,但概念是相同的,它们是由Erik Meijer和RxJava实现者创建的(如果适用于Java语言)。

这个页面会让你感兴趣(这是第二章):KeyTypes

在这里,您将在第一段中阅读:

使用 Rx 时,需要了解两种关键类型,以及可帮助您更有效地学习 Rx 的辅助类型子集。IObserver和IObservable构成了Rx的基本构建块,而ISubject的实现减少了Rx新手开发人员的学习曲线。

...

从本质上讲,Rx 是建立在观察者模式的基础上的。.NET 已经公开了一些其他方法来实现观察者模式,例如多播委托或事件(通常是多播委托)。

即使类型/API有点不同,你也会从这本书中学到很多东西,可能比一些博客要多得多。

这本书没有说什么...因为它在RxJava实现中)

RxJava的主要开发人员在这个时候引入了一个轻微的变化(见PR #792),允许区分两种类型的合同:

  • 通知 ->Observer
  • (取消)订阅 ->Subscription

此更改允许更好地表达/拆分 RxJava 库实现类的这些关注点。

但是,作为库用户,使用 RxJava 库的实际实现应该足够好。

实现订阅者需要更多的知识,工作和关怀,实际上订阅语义非常重要,具体取决于可观察的源的类型(热或冷?创建成本高昂?


在大多数情况下,公开而不是在上述情况下不会干扰代码,但除非需要这些非订阅语义,否则它不是它的预期用途。但最终实现一个,并且可能涉及陷入一些陷阱,例如:SubscriberObserverSubscriber

  1. 将资源用于不使用的功能
  2. 无法从其他类继承
  3. 编写不正确的取消订阅代码
  4. 复制/粘贴代码,不正确的代码或为不同上下文编写的正确代码

答案 2

(编辑:这显然只适用于RxJava 1。

  1. 是可以从数据源 (an ) 获取数据的对象。数据源通过调用观察者的 .ObserverObservableonNext()

  2. A 是也可以取消订阅该数据源(通过接口)的。SubscriberObserverSubscription

  3. 该函数试图返回汽车,但没有直接的方法可以做到这一点。但是有一个获取汽车详细信息()的函数,它将调用具有所有汽车详细信息的观察者。因此,它调用该函数并传递给它一个观察者,当它获得数据时,将从细节中获取汽车数据并将其传递给自己的观察者。getCar()getCarDetails()


推荐