首先看一段Map函数的使用代码:

        Observable.create(new Observable.OnSubscribe<Integer>() {
@Override
public void call(Subscriber<? super Integer> subscriber) {
subscriber.onNext(123);
}
}).map(new Func1<Integer, String>() { @Override
public String call(Integer integer) {
return integer.toString();
}
}).subscribe(new Subscriber<String>() {
public static final String TAG ="Test" ; @Override
public void onCompleted() {
} @Override
public void onError(Throwable e) {
} @Override
public void onNext(String s) {
Log.d(TAG, "onNext: "+s);
}
});

Observable<Integer>Observable1=Observable.create(new Observable.OnSubscribe<Integer>() {
    @Override

public void call(Subscriber<? super Integer> subscriber) { subscriber.onNext(123); }

});

create函数构建了一个新的Observable 在Observable的构造函数中将Observable.onSubscribe属性赋值为 Observable.OnSubscribe<Integer>;
Observable<String> Observable2= Observable1.map(new Func1<Integer, String>() {
     @Override
     public String call(Integer integer) {
     return null;
   }});
通过 map函数构建了一个新的Observable
map函数源码:
public final <R> Observable<R> map(Func1<? super T, ? extends R> func) {
     return lift(new OperatorMap<T, R>(func));
}
在map源码中首先通过func(这里的func指的就是Func1<Integer, String>())参数构建一个OperatorMap类;
public OperatorMap(Func1<? super T, ? extends R> transformer) {
   this.transformer = transformer;
}
OperatorMap.transformer 也指向了Func1<Integer, String>();

lift函数里面创建了一个新的Observable,而上边的Observable<String> Observable2也就是lift函数创建的;
public final <R> Observable<R> lift(final Operator<? extends R, ? super T> operator) {
return new Observable<R>(new OnSubscribeLift<T, R>(onSubscribe, operator));
}
public final class OnSubscribeLift<T, R> implements OnSubscribe<R>

在构造函数中传了一个OnSubscribeLift对象,因此Observable2.onSubscribe 也就指向了OnSubscribeLift;

public OnSubscribeLift(OnSubscribe<T> parent, Operator<? extends R, ? super T> operator) {
this.parent = parent;
this.operator = operator;
}
在OnSubscribeLift的构造函数中parent 被指向为Observable1中的OnSubscribe(Observable.OnSubscribe<Integer>())
operator指向OperatorMap;
通过Map函数就创建了一个新的Observable,所有开头的例子的代码就变成了
Observable2 .subscribe(new Subscriber<String>() {
public static final String TAG ="125" ;

@Override
public void onCompleted() {

}

@Override
public void onError(Throwable e) {

}

@Override
public void onNext(String s) {
Log.d(TAG, "onNext: "+s);
}
});
然后在分析下subscribe函数:
public final Subscription subscribe(Subscriber<? super T> subscriber) {
return Observable.subscribe(subscriber, this);
}
在Observable.subscribe(subscriber, this); 中的this 指向的是Observable2;

static <T> Subscription subscribe(Subscriber<? super T> subscriber, Observable<T> observable) {
.................
subscriber.onStart();
hook.onSubscribeStart(observable, observable.onSubscribe).call(subscriber);
return hook.onSubscribeReturn(subscriber);
.................
}
从subscribe函数代码可以看出,最终调用的是onSubscribe的call函数;
此时的onSubscribe指向的是Observable2.onSubscribe 也就是早lift函数中创建的OnSubscribeLift;
在OnSubscribeLift.java 代码中:
public void call(Subscriber<? super R> o) {
.............
Subscriber<? super T> st = hook.onLift(operator).call(o);

st.onStart();
parent.call(st);
............
}
在call函数中参数 Subscriber<? super R> o指向的是subscribe函数中的Subscriber<String>();
call函数的内部首先创建了一个新的 Subscriber<? super T> st;
此时的operator指向的是OperatorMap类
新的Subcriber(MapSubscriber对象)放入订阅列表中,以便最后一起把订阅对象释放。同时返回新的Subcriber。
public Subscriber<? super T> call(final Subscriber<? super R> o) {
   MapSubscriber<T, R> parent = new MapSubscriber<T, R>(o, transformer);
   o.add(parent);
   return parent;
}
static final class MapSubscriber<T, R> extends Subscriber<T> {
  public MapSubscriber(Subscriber<? super R> actual, Func1<? super T, ? extends R> mapper) {
   this.actual = actual;
   this.mapper = mapper;
  }
}
在OperatorMap类的call方法中创建了一个新的MapSubscriber对象;
在创建的MapSubscriber对象的构造函数中对字段进行赋值
actual 指向 o 也就是subscribe函数中的Subscriber<String>();
mapper 指向OperatorMap.transformer (指向了map函数的中参数Func1<Integer, String>())

回到在OnSubscribeLift.call 代码中,当创建好新的Subscriber对象后,将执行
parent.call(st);
此时的parent 指向的是Observable1中的OnSubscribe,因此调用的call方法相当于是
public void call(Subscriber<? super Integer> subscriber) {
  subscriber.onNext(123);
}
此时的subscriber 就是新建的st(MapSubscriber) 跳转到onNext函数中;
static final class MapSubscriber<T, R> extends Subscriber<T> {
public void onNext(T t) {
  R result;

try {
     result = mapper.call(t);
   } catch (Throwable ex) {
   Exceptions.throwIfFatal(ex);
   unsubscribe();
   onError(OnErrorThrowable.addValueAsLastCause(ex, t));
   return;
  }

actual.onNext(result);
}
}
此时的参数t为123;执行mapper.call(t);
mapper此时执行的是
public String call(Integer integer) {
return integer.toString();
}
result 就变为了"123";
然后在执行actual.onNext("123");
actual此时就是:
public void onNext(String s) {
Log.d(TAG, "onNext: "+s);
}

到现在为止,整个流程代码就分析完成了

RxJava 中的Map函数原理分析的更多相关文章

  1. map函数原理

    # -*- coding: utf-8 -*- #python 27 #xiaodeng #map函数 #map函数会对一个序列对象中的每一个元素应用被传入的函数,并返回一个包含了所有函数调用结果的一 ...

  2. perl编程中的map函数示例

    转自:http://www.jbxue.com/article/14854.html 发布:脚本学堂/Perl  编辑:JB01   2013-12-20 10:20:01  [大 中 小] 本文介绍 ...

  3. Python中的map()函数和reduce()函数的用法

    Python中的map()函数和reduce()函数的用法 这篇文章主要介绍了Python中的map()函数和reduce()函数的用法,代码基于Python2.x版本,需要的朋友可以参考下   Py ...

  4. python中的map()函数

    MapReduce的设计灵感来自于函数式编程,这里不打算提MapReduce,就拿python中的map()函数来学习一下. 文档中的介绍在这里: map(function, iterable, .. ...

  5. Python连载43-current中的map函数、xml文件

    一.current中的map函数 1.map(fn,*iterable,timeout=None) (1)跟map函数相类似(2)函数需要异步执行(3)timeout代表超时时间 (4)map和sub ...

  6. 关于boost中enable_shared_from_this类的原理分析

    首先要说明的一个问题是:如何安全地将this指针返回给调用者.一般来说,我们不能直接将this指针返回.想象这样的情况,该函数将this指针返回到外部某个变量保存,然后这个对象自身已经析构了,但外部变 ...

  7. 实现python中的map函数

    假设Python没有提供map()函数,自行编写my_map()函数实现与map()相同的功能.以下代码在Python 2.7.8中实现. 实现代码: def my_map(fun,num): i = ...

  8. Python 中的map函数,filter函数,reduce函数

      自学python,很多地方都需要恶补.       三个函数比较类似,都是应用于序列的内置函数.常见的序列包括list.tuple.str.   1.map函数 map函数会根据提供的函数对指定序 ...

  9. RxJava 中的map与flatMap

    1.map和flatMap都是接受一个函数作为参数(Func1) 2.map函数只有一个参数,参数一般是Func1,Func1的<I,O>I,O模版分别为输入和输出值的类型,实现Func1 ...

随机推荐

  1. js的同步异步

    由于js没有多线程,所以处理多任务的时候,可以用异步回调来解决.js中setTimeout.setInterval.ajax(jq中可以选择同步或异步)均会开启异步.遇到异步模块,会将其推入值任务队列 ...

  2. python之路 django2

    Django请求生命周期 首先:对于所有的web框架来说本质就是一个socket服务端,浏览器是socket客户端 路由系统 在Django的urls中我们可以根据一个URL对应一个函数名来定义路由规 ...

  3. visual studio开发工具的C#主流控件属性一览表

    visual studio开发工具的C#主流控件属性一览表 详细的介绍了各控制属性的详细中文介绍 C#控件及常用设计整理 1.窗体 1.常用属性 (1)Name属性:用来获取或设置窗体的名称,在应用程 ...

  4. tomcat高并发配置调优

    最近部署的tomcat,里面放了一个apk提供给测试人员测试,而有一天压测的时候,他们一致反馈下载不了,结果查看日志才发现如下错误: [html] view plain copy INFO: Maxi ...

  5. Spark高级数据分析· 3推荐引擎

    推荐算法流程 推荐算法 预备 wget http://www.iro.umontreal.ca/~lisa/datasets/profiledata_06-May-2005.tar.gz cd /Us ...

  6. Android系统init进程启动及init.rc全解析

    转:https://blog.csdn.net/zhonglunshun/article/details/78615980 服务启动机制system/core/init/init.c文件main函数中 ...

  7. yum安装memchache

    转载地址:http://www.cnblogs.com/jiunadianshi/articles/2001334.html 标准的CentOS5软件仓库里面是没有memcache相应的包的,所以,我 ...

  8. PHP+MySQL数据库编程的步骤

    第一步:PHP连接MySQL服务器 第二步:选择当前要操作的数据库 第三步:设置请求或返回的数据的字符集 第四步:执行各种SQL语句. PHP连接MySQL服务器 1.mysql_connect() ...

  9. ViewResolver和ResponseBody笔记

    处理HttpResponseBody有两种方式,ViewResolver(视图解析器)和ResponseBody ViewResolver.View多用于jsp,ViewResolver的主要作用是把 ...

  10. springboot集成shiro 前后端分离 统一处理shiro异常

    在前后端分离的情况下,shiro一些权限异常处理会返回401之类的结果,这种结果不好统一管理.我们希望的结果是统一管理,所有情况都受我们控制 就算权限验证失败,我们也希望返回200,并且返回我们定义的 ...