ReactiveCocoa是响应式编程(FRP)在IOS中的一个实现框架,它的开源地址为:https://github.com/ReactiveCocoa/ReactiveCocoa# ;在网上看了几篇文章,感觉理论讲了很多,但是代码还是看不太懂,于是自己把它github文档上的一些使用的经典示例实现了一下,项目中有需要时可以直接搬过去用,用的熟练了再读源码也比较容易理解。

例1. 监听对象的成员变量变化,当成员变量值被改变时,触发做一些事情。

这种情况其实就是IOS KVO机制使用的场景,使用KVO实现,通常有三个步骤:1,给对象的成员变量添加监听;2,实现监听回调;3,取消监听;而通过RAC可以直接实现,RAC的回调是通过block实现的,类似于过程式编程,上下文也更容易理解一些。

场景:当前类有一个成员变量 NSString *input,当它的值被改变时,发送一个请求。

实现:

  1. [RACObserve(self, input)
  2. subscribeNext:^(NSString* x){
  3. request(x);//发送一个请求
  4. }];

每次input值被修改时,就会调用此block,并且把修改后的值做为参数传进来。

场景:在上面场景中,当用户输入的值以2开头时,才发请求.

实现:

  1. [[RACObserve(self, input)
  2. filter:^(NSString* value){
  3. if ([value hasPrefix:@"2"]) {
  4. return YES;
  5. } else {
  6. return NO;
  7. }
  8. }]
  9. subscribeNext:^(NSString* x){
  10. request(x);//发送一个请求
  11. }];

场景:上面场景是监听自己的成员变量,如果想监听UITextField输入值变化,框架也做了封装可以代替系统回调

实现:

  1. [[self.priceInput.rac_textSignal
  2. filter:^(NSString *str) {
  3. if (str.integerValue > 20) {
  4. return YES;
  5. } else {
  6. return NO;
  7. }
  8. }]
  9. subscribeNext:^(NSString *str) {
  10. <span style="white-space:pre">    </span>request(x);//发送一个请求

}];


例2. 同时监听多个变量变化,当这些变量满足一定条件时,使button为可点击状态

场景:button监听 两个输入框有值和一个成员变量值,当输入框有输入且成员变量为真时,button为可点击状态

实现:

  1. RAC(self.payButton,enabled) = [RACSignal
  2. combineLatest:@[self.priceInput.rac_textSignal,
  3. self.nameInput.rac_textSignal,
  4. RACObserve(self, isConnected)
  5. ]
  6. reduce:^(NSString *price, NSString *name, NSNumber *connect){
  7. return @(price.length > 0 && name.length > 0 && [connect boolValue]);
  8. }];

场景:满足上面条件时,直接发送请求

实现:

  1. [[RACSignal
  2. combineLatest:@[self.priceInput.rac_textSignal,
  3. self.nameInput.rac_textSignal,
  4. RACObserve(self, isConnected)
  5. ]
  6. reduce:^(NSString *price, NSString *name, NSNumber *connect){
  7. return @(price.length > 0 && name.length > 0 && ![connect boolValue]);
  8. }]
  9. subscribeNext:^(NSNumber *res){
  10. if ([res boolValue]) {
  11. NSLog(@"XXXXX send request");
  12. }
  13. }];

例3. 类似于生成产-消费

场景:用户每次在TextField中输入一个字符,1秒内没有其它输入时,去发一个请求。TextField中字符改变触发事件已在例1中展示,这里实现一下它触法的方法,把1秒延时在此方法中实现。

实现:

  1. - (void)showLoading {
  2. [self.loadingDispose dispose];//上次信号还没处理,取消它(距离上次生成还不到1秒)
  3. @weakify(self);
  4. self.loadingDispose = [[[RACSignal createSignal:^RACDisposable *(id<RACSubscriber> subscriber) {
  5. [subscriber sendCompleted];
  6. return nil;
  7. }] delay:1] //延时一秒
  8. subscribeCompleted:^{
  9. @strongify(self);
  10. doRequest();
  11. self.loadingDispose = nil;
  12. }];
  13. }

上面代码看起来挻费解,不过下面一段类似的代码拆开写的,会比较容易理解:

  1. [self.loadingDispose dispose];
  2. RACSignal *loggingSignal = [RACSignal createSignal:^ RACDisposable * (id<RACSubscriber> subscriber) {//BLOCK_1
  3. subscriptions++;
  4. [subscriber sendNext:@"mytest"];
  5. [subscriber sendCompleted];
  6. return nil;
  7. }];
  8. loggingSignal = [loggingSignal delay:10];
  9. self.loadingDispose = [loggingSignal subscribeNext:^(NSString* x){//BLOCK_2
  10. NSLog(@"%@",x);
  11. NSLog(@"subscription %u", subscriptions);
  12. }];
  13. self.loadingDispose = [loggingSignal subscribeCompleted:^{//BLOCK_3
  14. NSLog(@"subscription %u", subscriptions);
  15. }];

loggingSignal在每次被调用subscriibeNext:^(id x)或subscribeCompleted:^方法时(12行和17行),它创建进传进的参数block_1就会被触动发,而block_1中的sendNext:方法会调用subscriibeNext:^中对应的block_2, 而block_1中的sendCompleted会调用subscribeCompleted:中对应的block_3

IOS响应式编程框架ReactiveCocoa(RAC)使用示例-备的更多相关文章

  1. IOS响应式编程框架ReactiveCocoa(RAC)使用示例

    ReactiveCocoa是响应式编程(FRP)在iOS中的一个实现框架,它的开源地址为:https://github.com/ReactiveCocoa/ReactiveCocoa# :在网上看了几 ...

  2. iOS响应式编程:ReactiveCocoa vs RxSwift 选谁好

    转载: iOS响应式编程:ReactiveCocoa vs RxSwift 选谁好 内容来自stack overflow的一个回答:ReactiveCocoa vs RxSwift – pros an ...

  3. [iOS] 响应式编程开发-ReactiveCocoa(一)

    什么是响应式编程 响应式编程是一种面向数据流和变化传播的编程范式.这意味着可以在编程语言中很方便地表达静态或动态的数据流,而相关的计算模型会自动将变化的值通过数据流进行传播. 例如,在命令式编程环境中 ...

  4. [iOS] 响应式编程开发-ReactiveCocoa(二)

    RAC实现图片下载功能 在实现异步RAC下载图片的过程中,需要注意以下几点: • 通过 NSURLConnection 对象的 +(RACSignal *)rac_sendAsynchronousRe ...

  5. 响应式布局框架 Pure-CSS 5.0 示例中文版-上

    0. Pure-CSS 介绍 Pure CSS 是雅虎出品的 CSS 框架, 依托于Normalize.CSS,在不适用任何JS代码情况下即可实现响应式布局的轻量级框架,无依赖,体积小. 1. CDN ...

  6. 响应式布局框架 Pure-CSS 5.0 示例中文版-中

    8. 表单 Form 在 form 标签中添加 .pure-form 类,可生成单行表单(inline) 效果图: 代码: <form class="pure-form"&g ...

  7. 响应式布局框架 Pure-CSS 5.0 示例中文版-下

    10. 表格 Tables 在 table 标签增加 .pure-table 类 <table class="pure-table"> <thead> &l ...

  8. ReactiveCocoa,最受欢迎的iOS函数响应式编程库(2.5版),没有之一!

    简介 项目主页: ReactiveCocoa 实例下载: https://github.com/ios122/ios122 简评: 最受欢迎,最有价值的iOS响应式编程库,没有之一!iOS MVVM模 ...

  9. [转帖]浅谈响应式编程(Reactive Programming)

    浅谈响应式编程(Reactive Programming) https://www.jianshu.com/p/1765f658200a 例子写的非常好呢. 0.9312018.02.14 21:22 ...

随机推荐

  1. E​F​I​主​板​和​G​P​T​分​区​表​安​装​系​统以及转换GPT分区表的方法

    现在硬盘越来越大,而原来的MBR分区方式,超过2T的硬盘就会识别不全,只有使用GPT的方式才可以,但是GPT如果用原来的BIOS是无法引导装系统了,不过如果你的主板支持EFI,那么可以用GPT+EFI ...

  2. cf E. Valera and Queries

    http://codeforces.com/contest/369/problem/E 题意:输入n,m; n 代表有多少个线段,m代表有多少个询问点集.每一个询问输出这些点的集合所占的线段的个数. ...

  3. BZOJ 2732 射箭

    http://www.lydsy.com/JudgeOnline/problem.php?id=2732 题意:给你n个靶子,让你求是否有一个经过原点的抛物线经过最多的前k个靶子,求出最大的k 思路: ...

  4. ASP.NET WEB API 如何使用基于Post的方式传递多个值(二)

    前面我曾经写过一篇文章,是基于HttpContext的请求上下文中读取表单参数,其实还可以将其单独拆分出来. 基于Filter的方式 获取表单值:(核心代码)   public void OnActi ...

  5. (转)失落的C语言结构体封装艺术

    目录1. 谁该阅读这篇文章 2. 我为什么写这篇文章 3.对齐要求 4.填充 5.结构体对齐及填充 6.结构体重排序 7.难以处理的标量的情况 8.可读性和缓存局部性 9.其他封装的技术 10.工具 ...

  6. [VBA]用一个简单例子说明如何在Excel中自定义函数

    Excel中的函数无疑是强大的,但是再强大的战士也有他脆弱的脚后跟[1].这两天在使用Excel的时候遇到了一个需求,要在某一个单元格里面自动计算今天是星期几(如显示 Today is Tuesday ...

  7. 黑马程序员_Java面向对象1_封装

    3.面向对象_封装 3.1面向对象概念 3.1.1理解面向对象 面向对象是相对面向过程而言 面向对象和面向过程都是一种思想 面向过程:强调的是功能行为(执行者) 面向对象:将功能封装进对象,强调具备了 ...

  8. <转载>无法解析的外部符号 _main,该符号在函数 ___tmainCRTStartup 中被引用

    转载http://blog.sina.com.cn/s/blog_6e6c5f230100p92p.html 无法解析的外部符号 _main,该符号在函数 ___tmainCRTStartup 中被引 ...

  9. day54

    今天复习时间15个小时 那都做了什么呢 数学2000试卷 阅读2篇整理 翻译2个视频 政治背诵加视频 数学综合5个证明 作文两篇 c语言结构体以及简单总结 博客园日记 数据结构 好了 感觉也没有做什么 ...

  10. python wmi模块学习

    # -*- coding: cp936 -*- import wmi c = wmi.WMI () for sys in c.Win32_OperatingSystem(): print " ...