RxSwift(二)----Subjects

RxSwift(二)----Subjects

在RxSwift中有一种东西既能当做observable,又能当做observer,这种就是Subject.在RxSwift中有四种类型的Subject:

  • PublishSubject,初始元素为空,只把新元素发送给其订阅者.
  • BehaviorSubject,有初始元素,把最近的元素发送器订阅者.
  • ReplaySubject,会缓存一定数量的元素,并将发送给器新订阅者.
  • Variable,对BehaviorSubject的封装,将初始值或最近的值发送给其订阅者.

PublishSubject

Snip20181127_14.png

如果只是将新元素发送给订阅者直到订阅者取消订阅或者subject发出.completed或者.error事件为止.

let subject = PublishSubject<String>()
subject.onNext("hello world!")
let subscriptionOne = subject.subscribe { event in
    print(event)
}
subject.on(.next("1"))
subject.onNext("2")
    
let subscriptionTwo = subject.subscribe { event in
    print("2) ", event.element ?? event)
}
subject.onNext("3")
    
subscriptionOne.dispose()
subject.onNext("4")
    
subject.onCompleted()
subject.onNext("5")
subscriptionTwo.dispose()
    
let bag = DisposeBag()
subject.subscribe {
    print("3) ",$0.element ?? $0)
}
    .disposed(by: bag)

打印如下:

next(1)
next(2)
next(3)
2)  3
2)  4
2)  completed
3)  completed

如果subject发出.completed或者.error,这些都称为完成事件,它将发送这些完成事件给它将来的订阅者,不会发出.next()事件.这样不仅仅可以知道它什么时候终止,还可以知道你可能订阅了一个已经终止了的subject.

BehaviorSubject

Snip20181127_15.png

BehaviorSubject它初始化一个元素,它将最近的元素发送其订阅者.

let subject = BehaviorSubject(value: "hello world!")
let bag = DisposeBag()
// 初始值
subject.subscribe { event in
    print("1) ",(event.element ?? event.error) ?? event)
}
    .disposed(by: bag)
    
subject.onError(MyError.anError)
    
subject.subscribe {
     print("2) ",($0.element ?? $0.error) ?? $0)
}
    .disposed(by: bag)

打印如下:

1)  hello world!
1)  anError
2)  anError

因为BehaviorSubject它将最近的元素发送给订阅者,所以它必须初始化一个元素,如果你不带初始化元素,你可以用PublishSubject代替.

ReplaySubject

Snip20181127_16.png

ReplaySubject会缓存最近的元素,并将缓存的元素发送给其订阅者.

let subject = ReplaySubject<String>.create(bufferSize: 2)
let bag = DisposeBag()
    
subject.onNext("1")
subject.onNext("2")
subject.onNext("3")
    
subject.subscribe { event in
    print("1) ",(event.element ?? event.error) ?? event)
}
    .disposed(by: bag)
    
subject.subscribe {
    print("2) ",($0.element ?? $0.error) ?? $0)
}
    .disposed(by: bag)
    
subject.onNext("4")
subject.onError(MyError.anError)
subject.subscribe {
    print("3) ",($0.element ?? $0.error) ?? $0)
}
    .disposed(by: bag)

打印如下:

1)  2
1)  3
2)  2
2)  3
1)  4
2)  4
1)  anError
2)  anError
3)  3
3)  4
3)  anError

如果你缓存的元素太多的话,且是图片对象,这样对内存造成压力,或者是或者的元素是数组,这样也会有很大的缓存压力.

Variables

Variable是对BehaviorSubject的包装,并储存当前的值作为状态,你可以使用value属性获取或者设置值,这样可以不用onNext(_:)方法,

let variable = Variable("hello world!")
let bag = DisposeBag()
variable.value = "hello swift!"
variable.asObservable().subscribe {
     print("1) ",($0.element ?? $0.error) ?? $0)
}
    .disposed(by: bag)
    
variable.value = "1"
variable.asObservable().subscribe {
     print("2) ",($0.element ?? $0.error) ?? $0)
}
    .disposed(by: bag)
variable.value = "2"

打印如下:

1)  hello swift!
1)  1
2)  1
1)  2
2)  2

Variable不能添加.error.completed事件,否则编译器会产生错误.

©著作权归作者所有,转载或内容合作请联系作者
平台声明:文章内容(如有图片或视频亦包括在内)由作者上传并发布,文章内容仅代表作者本人观点,简书系信息发布平台,仅提供信息存储服务。

推荐阅读更多精彩内容

  • 本文章内部分图片资源来自RayWenderlich.com 本文结合自己的理解来总结介绍一下RxSwift最基本的...
    FKSky阅读 7,952评论 4 14
  • 最近比较忙,更新得有点慢,望谅解。 什么是Subject? 上一章我介绍了Observable——一个功能就像一条...
    turtleeeee阅读 5,863评论 2 14
  • 发现 关注 消息 RxSwift入坑解读-你所需要知道的各种概念 沸沸腾关注 2016.11.27 19:11*字...
    枫叶1234阅读 7,809评论 0 2
  • 最近在学习RxSwift相关的内容,在这里记录一些基本的知识点,以便今后查阅。 Observable 在RxSwi...
    L_Zephyr阅读 5,722评论 1 4
  • 早晨被黄鹂的怪叫叫醒,起来步出房门,在太阳升起前,院子里空气清凉适意。 家房前房后是两个小园子,前...
    野落篱边阅读 2,635评论 8 4