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

Mar*_*usH 79 java rx-java

我试图破译以下功能:

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

我从http://blog.danlew.net/2014/09/15/grokking-rxjava-part-1/获得了rxjava的一个很好的介绍,但它只是提到了Observer,说你将使用Subscriber的大部分内容.从Observable发出的消费品的时间.

有人可以向我解释

  1. 什么是观察者?
  2. 观察者与订阅者的不同之处是什么?
  3. 上面的代码片段做了什么?

Javadoc使它看起来像订阅者.订阅者的javadoc说它实现了观察者和订阅.我很迷茫.

Bri*_*ice 60

编辑:@ Alrid的评论

TL;博士

public abstract class Subscriber<T> implements Observer<T>, Subscription
Run Code Online (Sandbox Code Playgroud)

因此,SubscriberObserver的一个实现,在订阅时有额外的语义(更多的是关于取消订阅).你问题中的代码只是表明它通过了Observer接口而不是实现(通常的编程实践).

此代码也返回一个Subscription,这可能是因为此代码的作者认为客户端应该只能访问Subscription方法,而无法访问observable生成的元素.这可能是程序员错误.

很长的故事

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

此页面将引起您的兴趣(这是第二章):KeyTypes

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

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

...

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

即使类型/ API有点不同,您也会从本书中学到很多东西,可能比一些博客更多.

这是什么不说(...因为它是在RxJava执行)

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

  • 通知 - > Observer
  • (联合国)订阅 - > Subscription

此更改允许更好地表达/拆分RxJava库的实现类的这些问题.

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

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


在大多数情况下,暴露Subscriber而不是Observer在上面的情况下不会干扰代码,但除非需要那些非订阅语义,否则它不是它的预期用途.但最终实施一个Subscriber,并可能涉及到一些陷阱,如:

  1. 将资源用于您不会使用的功能
  2. 不能从另一个类继承
  3. 写错误的非订阅代码
  4. 复制/粘贴代码不正确的代码或为不同的上下文编写的正确代码

  • 在2.x中Observer用于订阅Observable,而Subscriber用于订阅Flowable,Subscriber不再实现Observer,https://github.com/ReactiveX/RxJava/issues/4515 (2认同)

Law*_*oot 37

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

  1. An Observer是可以从数据源(an Observable)获取数据的对象.数据源通过调用观察者将数据推送到它onNext().

  2. A SubscriberObserver可以取消订阅该数据源(通过Subscription界面).

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

  • 从RxJava 2开始就不是这样,订阅者和观察者是两个完全不同的接口.没有扩展另一个 (2认同)

Yar*_*hiy 18

在RxJava 2中 org.reactivestreams.Subscriber是符合Reactive Streams规范的接口.

主要区别Observable在于新Subscriber支持背压.

Observer是subscibed Observable,并Subscriber订阅Flowable(implements org.reactivestreams.Publisher).

见详细描述这里.