代码:

const a = of([1, 2, 3]);
a.subscribe((data) => console.log('Fairy:' + data));

单步调试,首先执行of所在的index.ts:

of.js的实现很简单:

import { isScheduler } from '../util/isScheduler';
import { fromArray } from './fromArray';
import { scheduleArray } from '../scheduled/scheduleArray';
export function of(...args) {let scheduler = args[args.length - 1];if (isScheduler(scheduler)) {args.pop();return scheduleArray(args, scheduler);}else {return fromArray(args);}
}
//# sourceMappingURL=of.js.map

没有scheduler,走fromArray这条路:

fromArray.js的实现:

import { Observable } from '../Observable';
import { subscribeToArray } from '../util/subscribeToArray';
import { scheduleArray } from '../scheduled/scheduleArray';
export function fromArray(input, scheduler) {if (!scheduler) {return new Observable(subscribeToArray(input));}else {return scheduleArray(input, scheduler);}
}
//# sourceMappingURL=fromArray.js.map

这个subscribeToArray是一个函数构造器,接收一个数组,返回一个新的函数:

export const subscribeToArray = (array) => (subscriber) => {for (let i = 0, len = array.length; i < len && !subscriber.closed; i++) {subscriber.next(array[i]);}subscriber.complete();
};
//# sourceMappingURL=subscribeToArray.js.map

该函数和我们在应用代码里调用Observable对象的subscribe方法时传入的回调函数有何区别?

继续往下调试。

调用Observable对象的subscribe方法:

ObserverOrNext就是上图第63行的箭头函数,error和complete为undefined:

新建一个Subscriber对象:

subscriber的父类是subscription:

subscriber的destination是一个SafeSubscriber:

SafeSubscriber也是一个Subscriber:

这个emptyObservable啥实现也没有:

import { config } from './config';
import { hostReportError } from './util/hostReportError';
export const empty = {closed: true,next(value) { },error(err) {if (config.useDeprecatedSynchronousErrorHandling) {throw err;}else {hostReportError(err);}},complete() { }
};
//# sourceMappingURL=Observer.js.map
ExtensibilityExtensibility![](https://img-blog.csdnimg.cn/img_convert/fd30a74f127e31a732add12cbcbabc05.png)所以toSubscriber返回的实际是一个subscriber对象:![](https://img-blog.csdnimg.cn/img_convert/d755db210f9042167caa4c3f8e51fbae.png)
![](https://img-blog.csdnimg.cn/img_convert/d7a08902cbd7f7c2cf54a7e8e440be08.png)首先调用subscriber对象的add方法,目的是通过这个三元表达式,判断到底应该调用subscribe方法,还是trySubscribe方法:![](https://img-blog.csdnimg.cn/img_convert/7842df68ea5df9dff9665ee002a0e0bc.png)在我的Angular10,执行后者:![](https://img-blog.csdnimg.cn/img_convert/fc35352eb8125afd3f4cb34c2b936136.png)记住这个语义:Observable的subscribe方法,输入参数为subscriber:![](https://img-blog.csdnimg.cn/img_convert/39930d88fe8b1b7febc9db45584dd876.png)_trySubscribe调用_subscribe:![](https://img-blog.csdnimg.cn/img_convert/c8255b7f4b351bcc80ad7d008b684cf8.png)然后就执行到了之前用subscribeToArray返回的function内部:![](https://img-blog.csdnimg.cn/img_convert/cca17064851f45b8998808a521e16e92.png)注意在这个上下文里,我们既有输入,又有应用程序传入的subscribe函数,因此可以调用next了:![](https://img-blog.csdnimg.cn/img_convert/00b5a512ad77740193ee1d209d188051.png)
![](https://img-blog.csdnimg.cn/img_convert/d6a9930cec4e5d881e6b3a104bda7da3.png)next和_next的区别就在于有个this.isStopped的判断:![](https://img-blog.csdnimg.cn/img_convert/4368c8a5e31f1c595616f2b666383b46.png)注意语义:Observable调用subscribe,而subscriber调用next.![](https://img-blog.csdnimg.cn/img_convert/ed88af507bbecd6b570cdb7dbd887e6f.png)subscriber的desination里包含了应用程序传入的callback:![](https://img-blog.csdnimg.cn/img_convert/831d2d80553d2ee5723196289f8446a5.png)
![](https://img-blog.csdnimg.cn/img_convert/7934c01b71638f69ce2595b6ed3a976f.png)subscriber的_tryOrUnsub函数里,最终调用应用程序的callback:![](https://img-blog.csdnimg.cn/img_convert/4309fcce0db382818f54641af6e04d75.png)
![](https://img-blog.csdnimg.cn/img_convert/f3c9f2197cb9c5812245324c029aee24.png)更多Jerry的原创文章,尽在:"汪子熙":
![](https://img-blog.csdnimg.cn/img_convert/e4a8387dca5921e049fd05f96ef232ae.png)

rxjs of操作符生成的Observable对象的执行详细分析相关推荐

  1. rxjs of操作符里subscribeToArray的实现原理示意图及分析

    写一段简单的代码来测试subscribeToArray: test1(){const subscribeToArray = (array) => (subscriber) => {for ...

  2. 生成式对抗网络GAN之实现手写字体的生成(基于keras Tensorflow2.0实现)详细分析训练过程和代码

  3. CGLIB动态代理对象执行流程分析

    前言 都说CGLIB动态代理对象执行方法的速度相较于JDK动态代理更快,那么为什么更快,实际是因为CGLIB中采用了FastClass机制,本篇文章将对CGLIB动态代理对象执行某一个方法的流程进行分 ...

  4. rxjs里的Observable对象和map配合的一个用法

    源代码: import { of } from 'rxjs'; import { Injectable } from '@angular/core'; import { map } from 'rxj ...

  5. rxjs里的Observable对象如何消费

    测试代码: import { of } from 'rxjs'; import { Injectable } from '@angular/core';@Injectable() export cla ...

  6. java hashmap 初始化赋值_HashMap引用传递,对象直接赋值,修改的是同一个对象,new HashMap「」(Map)才是生成新的对象...

    HashMap引用传递:对象直接赋值,修改的是同一个对象 MapsrcMap = new HashMap<>(); srcMap.put("a","a&quo ...

  7. Eclipse自动生成返回值对象与补全与加注释

    1.Eclipse自动生成返回值对象,将光标放在;后面按ctrl+1,弹出 Assign statement to new local varible,enter即可. 2.移动代码块快捷键:Alt+ ...

  8. 从调试器里观察到的Observable对象反推出其赋值的源代码位置

    展开Observable对象,从其operator能观察到施加在该Observable对象上的操作: Map操作:(event) => this.getBreakpoint(event.targ ...

  9. rxjs of操作符传入数组的单步执行

    源代码: const a = of([1, 2, 3]);const b = a.pipe(map((data) => {for( let i = 0; i < data.length; ...

最新文章

  1. 2021年大数据Hadoop(十二):HDFS的API操作
  2. 【网站汇总】安装教程系列
  3. ES6深入学习记录(一)class方法相关
  4. 2021年人工神经网络第一次作业要求
  5. MATLAB从入门到精通:MATLAB识别 自带手写数字集的CNN(LeNet5)
  6. Visual Studio 2010 Ultimate开发与测试敏捷特性
  7. java字符串10_排名前10的Java字符串问题
  8. Java——String类的方法
  9. 英文书《用unreal来学习c++》_用机器学习来概括《哈利波特》,四句话总结一场戏...
  10. 总结各类损失函数【修】
  11. javascript-流程控制-循环-分支-三元运算符
  12. Azure站点恢复之----VMM 站点到ASR
  13. java中什么是字节流和字符流_java中字节流与字符流的区别是什么
  14. CAD图纸可以约束转换后图纸格式的大小吗?
  15. 几种码农使用的等宽字体比较——让自己的眼睛爽起来!
  16. 学学就能进步之LM358介绍
  17. APISpace 绕口令API接口 免费好用
  18. 软件测试中单元测试,集成测试,系统测试,验收测试的区别
  19. C/C++获取系统IP地址
  20. matlab的subplot--子图位置大小随心所欲

热门文章

  1. Python解惑:整数比较
  2. makefile例子《一》
  3. Visual Studio 2008 Windows Server 2008 预发布-20日在南宁
  4. 配置phpmyadmin的认证方式 wamp下的phpmyadmin密码修改
  5. Vue -- 项目报错整理(1):RangeError: Maximum call stack size exceeded
  6. CKEditor5 基本使用
  7. Linux 常用解压和压缩命令
  8. ajaxfileupload踩过的坑
  9. Perl BEGIN块和END块
  10. 树——axure线框图部件库介绍