RXJS Observable的冷,热和Subject
一、Observable的冷和热
Observable 热:直播。所有的观察者,无论进来的早还是晚,看到的是同样内容的同样进度,订阅的时候得到的都是最新时刻发送的值。
Observable 冷:点播。 新的订阅者每次从头开始。
冷的Observable例子:
一开始有个订阅者,
两秒后又有个订阅者,这两个序列按照自己的节奏走的,不同步。每个流进行都会从interval的0开始。
console.log('RxJS included?', !!Rx); const count$ = Rx.Observable.interval().take();
const sub1 = count$.subscribe((val)=>{
console.log(val);
}); setTimeout(function(){
const sub2 = count$.subscribe((val)=>{
console.log(val);
});
},);
热的Observable例子
第二个订阅者直接从2开始起,跟第一个订阅者看到的内容是一样的。
const count$ = Rx.Observable.interval(1000).take(5).share();
const sub1 = count$.subscribe((val)=>{
console.log(val);
}); setTimeout(function(){
const sub2 = count$.subscribe((val)=>{
console.log(val);
});
},2000);
二、Subject
Subject即是观察者Observer,也是被观察对象Observable,同时实现了这两个接口。
意味着
- 一方面它可以作为流的组成的一方,输出的一方。
- 另一方面,它可以作为流的观察一方,接收一方。
Subject分为ReplaySubject和BehaviorSubject。
ReplaySubject:这种Subject会保留最新的n个值。
BehaviorSubject:是ReplaySubject的特殊形式。 保留最新的一个值。
【20200529】
拿subject做一个observer观察者,看Observable会丢什么东西出来,由它对外广播出去。
再拿subject去订阅两个观察者。
有n个observable去订阅subject,但是subject只会发出一个订阅的要求订阅原始observable。
1、subscribe的等价写法
subscribe 后面写的一个函数,相当于语法糖,快捷方式,临时创建冷一个observer对象。
默认情况应该是传入一个observer对象。
console.log('RxJS included?', !!Rx); const counter$ = Rx.Observable.interval(1000).take(5); const subject = new Rx.Subject(); const observer1 = {
next: (val)=>{console.log('1: ' +val);},
error: (err)=>{console.log('ERROR>> 1:'+ err);},
complete: ()=>{console.log('1 is complete');}
} const observer2 = {
next: (val)=>{console.log('2: ' +val);},
error: (err)=>{console.log('ERROR>> 2:'+ err);},
complete: ()=>{console.log('2 is complete');}
} //等价写法
counter$.subscribe(val =>{console.log(val);});
counter$.subscribe(observer2);
2、两个observer ,两次subscribe
console.log('RxJS included?', !!Rx); const counter$ = Rx.Observable.interval(1000).take(5); const subject = new Rx.Subject(); const observer1 = {
next: (val)=>{console.log('1: ' +val);},
error: (err)=>{console.log('ERROR>> 1:'+ err);},
complete: ()=>{console.log('1 is complete');}
} const observer2 = {
next: (val)=>{console.log('2: ' +val);},
error: (err)=>{console.log('ERROR>> 2:'+ err);},
complete: ()=>{console.log('2 is complete');}
} counter$.subscribe(observer1); setTimeout(function(){
counter$.subscribe(observer2);
},2000);
问题:需要在两处执行subscribe,很多情况下是这样的,定义好这些序列应该在什么时候被触发,我执行执行一句subscribe(),两个序列都会这么执行。这种情况下就需要用subject()。
3、subject
subject即使observable,因为它可以subscribe observer。
也是observer,因为它可以被observable subscribe。
console.log('RxJS included?', !!Rx); const counter$ = Rx.Observable.interval(1000).take(5); const subject = new Rx.Subject(); const observer1 = {
next: (val)=>{console.log('1: ' +val);},
error: (err)=>{console.log('ERROR>> 1:'+ err);},
complete: ()=>{console.log('1 is complete');}
} const observer2 = {
next: (val)=>{console.log('2: ' +val);},
error: (err)=>{console.log('ERROR>> 2:'+ err);},
complete: ()=>{console.log('2 is complete');}
} //不再用counter$去subscribe,用subject去subscribe,
subject.subscribe(observer1); setTimeout(function(){
subject.subscribe(observer2);
},2000); //定义好两边后,用counter$去subscribe
counter$.subscribe(subject);
用一句执行counter$.subscribe(subject),把定义好的序列,包括等待2秒的序列全部完成了。
4,subject是一个hot observable
往流里推送新值
第二个拿不到新值,因为第二个流订阅的时候,两个新值已经过去了。
5,ReplaySubject
replay把过去发生的事件进行重播。
ReplaySubject(2)把过去的2个事件进行重播。这样observer1 subscribe的时候就可以看到10和11。
6、BehaviorSubject只记住最新的值
总有一个最新值,总记住上一次的最新值
console.log('RxJS included?', !!Rx); const counter$ = Rx.Observable.interval(1000).take(5); const subject = new Rx.BehaviorSubject(); subject.next(10);
subject.next(11);
const observer1 = {
next: (val)=>{console.log('1: ' +val);},
error: (err)=>{console.log('ERROR>> 1:'+ err);},
complete: ()=>{console.log('1 is complete');}
} const observer2 = {
next: (val)=>{console.log('2: ' +val);},
error: (err)=>{console.log('ERROR>> 2:'+ err);},
complete: ()=>{console.log('2 is complete');}
} //不再用counter$去subscribe,用subject去subscribe,
subject.subscribe(observer1); setTimeout(function(){
subject.subscribe(observer2);
},2000); //定义好两边后,用counter$去subscribe
counter$.subscribe(subject);
取值的时候,会取得到最新的data,尽管在取值的时候也就是subscribre的时候值已经发射完了,尽管时机已经错失了还是能够得到它上一次发射之后的最新的一个值。
三、Angular中对Rx的支持
大量内置Observable支持:如Http,ReactiveForms,Route等。
Async Pipe是什么?有什么用?
Observable需要subscribe 一下,成员数组变量等于Observable得到的值。
使用Async Pipe可以直接使用Observable,还不用去取消订阅。
memberResults$: Observable<User[]>;
本文作者starof,因知识本身在变化,作者也在不断学习成长,文章内容也不定时更新,为避免误导读者,方便追根溯源,请诸位转载注明出处:https://www.cnblogs.com/starof/p/10505617.html 有问题欢迎与我讨论,共同进步。
RXJS Observable的冷,热和Subject的更多相关文章
- 怎样在RxJS Observable中使用Async-Await
怎样在RxJS Observable中使用Async-Await 一般情况下 async-await 和 Observables 并不能“在一起使用”.但RxJS 从一开始就具备与 Promises ...
- [RxJS] Split an RxJS Observable into groups with groupBy
groupBy() is another RxJS operator to create higher order observables. In this lesson we will learn ...
- [RxJS] Split an RxJS observable conditionally with windowToggle
There are variants of the window operator that allow you to split RxJS observables in different ways ...
- [RxJS] Split an RxJS observable with window
Mapping the values of an observable to many inner observables is not the only way to create a higher ...
- 简单模拟实现Rxjs Observable
1.先定义类型 export type Observer = { next: (any) => void, complete?: (any) => void, } export inter ...
- Angular 4+ Http
HTTP: 使应用能够对远端服务器发起相应的Http调用: 你要知道: HttpModule并不是Angular的核心模块,它是Angualr用来进行Web访问的一种可选方式,并位于一个名叫@angu ...
- Angular基础(八) Observable & RxJS
对于一个应用来说,获取数据的方法可以有很多,比如:Ajax, Websockets, LocalStorage, Indexdb, Service Workers,但是如何整合多种数据源.如何避免BU ...
- RxJS之Subject主题 ( Angular环境 )
一 Subject主题 Subject是Observable的子类.- Subject是多播的,允许将值多播给多个观察者.普通的 Observable 是单播的. 在 Subject 的内部,subs ...
- RxJS - Subject(转)
Observer Pattern 观察者模式定义 观察者模式又叫发布订阅模式(Publish/Subscribe),它定义了一种一对多的关系,让多个观察者对象同时监听某一个主题对象,这个主题对象的状态 ...
随机推荐
- Django中related_name作用
相当于我们使用related代替了在通过一个对象查询出多个对象集合时,使用表名_set来获取 我先定义两个模型,一个是作者,一个是作者出版的书籍,算是一对多的类型. class Person(mode ...
- mysql 修改表结构、表字段注释语句
虽然现在有各种各样的工具可以直接对表结构进行修改,但是我还是喜欢使用语句进行修改.以下语句是对表增加字段.给字段加注释的语句 alter table orders add column isupdyq ...
- 服务器配置 ssl 证书
最近因为公司的 服务器 ssl证书即将到期(服务器 和 ssl证书管理都在 腾讯云上), 所以为了能顺利的 重新申请 ssl证书 ,我和小伙伴 在他的个人服务器上尝试了一波(我们居然都不会 ...) ...
- CentOS部署yapi
转载自 https://www.linuxidc.com/Linux/2018-01/150513.htm 在mongoDB添加yum源时,源路径有修改,原文中的路径404不可用 一.准备工作 1.1 ...
- ACM-ICPC 2018 沈阳赛区网络预赛 B Call of Accepted(表达式求值)
https://nanti.jisuanke.com/t/31443 题意 给出一个表达式,求最小值和最大值. 表达式中的运算符只有'+'.'-'.'*'.'d',xdy 表示一个 y 面的骰子 ro ...
- PMP知识点(五)——配置管理
配置控制重点关注可交付成果及各个过程的技术规范,而变更控制则着眼于识别.记录.批准或否决对项目文件,可交付成果或基准的变更. 包括在实施整体变更控制过程中的部分配置管理活动有: 1.配置识别. 识别与 ...
- vue+element-ui实现显示隐藏密码
<template> <el-form :model="cuser_info" label-width="115px" label-posit ...
- 安装hue及hadoop和hive整合
环境: centos7 jdk1.8.0_111 Hadoop 2.7.3 Hive1.2.2 hue-3.10.0 Hue安装: 1.下载hue-3.10.0.tgz: https://dl.dro ...
- js reduce()方法使用
reduce() 方法接收一个函数作为累加器,数组中的每个值(从左到右)开始缩减,最终计算为一个值. reduce() 可以作为一个高阶函数,用于函数的 compose. 注意: reduce() 对 ...
- 看不到git远程分支
1.先用fetch命令更新remote索引 $ git fetch 2.再查看remote分支,发现已经可以看到目标分支 $ git branch -a 3.再切换分支 $ git checkout ...