简述
提到 ReactiveCocoa(以下简称RAC),很容易让人联想到 Swift 中广泛使用的一个响应式编程框架 RxSwift。顾名思义,RAC 带着 Cocoa 说明它对 Cocoa 的支持要更好一些, 虽然 RxSwift 也对 Cocoa 做了相应的支持,但是从官方文档上也可以说明, RAC 确实对 Cocoa 的支持要比 Swift 要更广泛一些,RAC 的最终目的也是更可能偏向对 Cocoa 的支持。
1、never 信号
创建一个不发送 next 事件,也没有完成事件的信号。
RACSignal *signal = [RACSignal never];
[signal subscribeNext:^(id _Nullable x) {
NSLog(@"%@",x);
} completed:^{
NSLog(@"%@",@"done");
}];
Result:
没有任何打印信息,因为不会有 next 或者 完成事件被订阅者接收到。
2、empty 信号
创建一个只能发送完成信号的信号
RACSignal *signal = [RACSignal empty];
[signal subscribeNext:^(id _Nullable x) {
NSLog(@"%@",x);
} completed:^{
NSLog(@"%@",@"done");
}];
Result:
2017-08-21 15:55:05.114459+0800 ReactiveCocoaDemo[331:43141] done
3、create 操作
这里演示了一个数组转换成序列并转换成信号,该信号被订阅后输出的例子。
NSArray *array = @[@1, @2, @3, @4, @5]; //创建一个数组
[[[array.rac_sequence signalWithScheduler:RACScheduler.mainThreadScheduler] //将数组转换成序列再转换成可以被订阅的信号
map:^id _Nullable(NSNumber *value) {
return @(2 * value.integerValue); //map
}]
subscribeNext:^( NSNumber *num) { // 订阅信号并且接收 next 事件
NSLog(@"%@",num);
} completed:^{ // 完成事件
NSLog(@"done");
}];
Result:
2017-08-18 21:25:38.166 ReactiveCocoaDemo[2807:37246] 1
2017-08-18 21:25:38.166 ReactiveCocoaDemo[2807:37246] 2
2017-08-18 21:25:38.167 ReactiveCocoaDemo[2807:37246] 3
2017-08-18 21:25:38.167 ReactiveCocoaDemo[2807:37246] 4
2017-08-18 21:25:38.167 ReactiveCocoaDemo[2807:37246] 5
2017-08-18 21:25:38.168 ReactiveCocoaDemo[2807:37246] done
4、map 操作
有接触过具有高阶的开发语言的朋友们应该对 map 、filter 不陌生。比如 es6, python 等等。map 在 RAC 中相当于偷梁换柱,在信号发出后到被订阅之间被劫持更改了,同样使用这个例子
NSArray *array = @[@1, @2, @3, @4, @5]; //创建一个数组
[[[array.rac_sequence signalWithScheduler:RACScheduler.mainThreadScheduler] //将数组转换成序列再转换成可以被订阅的信号
map:^id _Nullable(NSNumber *value) {
return @(2 * value.integerValue); //map
}]
subscribeNext:^( NSNumber *num) { // 订阅信号并且接收 next 事件
NSLog(@"%@",num);
} completed:^{ // 完成事件
NSLog(@"done");
}];
Result:
2017-08-18 22:09:23.978 ReactiveCocoaDemo[2887:58573] 2
2017-08-18 22:09:23.978 ReactiveCocoaDemo[2887:58573] 4
2017-08-18 22:09:23.978 ReactiveCocoaDemo[2887:58573] 6
2017-08-18 22:09:23.979 ReactiveCocoaDemo[2887:58573] 8
2017-08-18 22:09:23.979 ReactiveCocoaDemo[2887:58573] 10
2017-08-18 22:09:23.979 ReactiveCocoaDemo[2887:58573] done
可以看到数据已经被更改。
5、filter 操作
filter在英文中被翻译成漏斗,意思就是过滤的意思。功能就是过滤出有用的东西,下面是例子
NSArray *array = @[@1, @2, @3, @4, @5]; //创建一个数组
[[[array.rac_sequence signalWithScheduler:RACScheduler.mainThreadScheduler] //将数组转换成序列再转换成可以被订阅的信号
filter:^BOOL(NSNumber *value) {
return value.integerValue > 3; //过滤值大于三的值
}]
subscribeNext:^( NSNumber *num) { // 订阅信号并且接收 next 事件
NSLog(@"%@",num);
} completed:^{ // 完成事件
NSLog(@"done");
}];
Result:
2017-08-19 08:11:34.864 ReactiveCocoaDemo[3033:69014] 4
2017-08-19 08:11:34.865 ReactiveCocoaDemo[3033:69014] 5
2017-08-19 08:11:34.865 ReactiveCocoaDemo[3033:69014] done
6、take 操作
意思是取前多少个信号发送的next 的 value。
NSArray *array = @[@1, @2, @3, @4, @5]; //创建一个数组
[[[array.rac_sequence signalWithScheduler:RACScheduler.mainThreadScheduler] //将数组转换成序列再转换成可以被订阅的信号
take:1] //只取一个
subscribeNext:^( NSNumber *num) { // 订阅信号并且接收 next 事件
NSLog(@"%@",num);
} completed:^{ // 完成事件
NSLog(@"done");
}];
Result:
2017-08-21 15:30:24.419852+0800 ReactiveCocoaDemo[310:36453] 1
2017-08-21 15:30:24.420186+0800 ReactiveCocoaDemo[310:36453] done
7、skip 操作
与 take 相对应,take 可理解为取前多少个value,skip 则意味着跳过前多少个value
NSArray *array = @[@1, @2, @3, @4, @5]; //创建一个数组
[[[array.rac_sequence signalWithScheduler:RACScheduler.mainThreadScheduler] //将数组转换成序列再转换成可以被订阅的信号
skip:2] //跳过多少个value
subscribeNext:^( NSNumber *num) { // 订阅信号并且接收 next 事件
NSLog(@"%@",num);
} completed:^{ // 完成事件
NSLog(@"done");
}];
Result:
2017-08-21 15:35:17.137181+0800 ReactiveCocoaDemo[314:37812] 3
2017-08-21 15:35:17.137516+0800 ReactiveCocoaDemo[314:37812] 4
2017-08-21 15:35:17.137778+0800 ReactiveCocoaDemo[314:37812] 5
2017-08-21 15:35:17.138075+0800 ReactiveCocoaDemo[314:37812] done
8、return 操作
return 可以快速通过一个值来创建一个信号,主要应用在和其他的值进行合并,传递一些数据到上下文。
RACSignal *numSignal = [RACSignal return:@"Hello"];
[numSignal subscribeNext:^(id _Nullable x) {
NSLog(@"%@",x);
} completed:^{
NSLog(@"%@",@"done");
}];
Result:
2017-08-21 15:05:23.923483+0800 ReactiveCocoaDemo[295:30109] Hello
2017-08-21 15:05:23.923722+0800 ReactiveCocoaDemo[295:30109] done
9、ignore 操作
顾名思义,ignore 为忽略指定的 value ,可以串联多个来忽略多个 value
NSArray *numArray = @[@1, @2, @3, @4, @5];// 创建一个数字数组
[[[[numArray.rac_sequence signalWithScheduler:RACScheduler.mainThreadScheduler] //序列转为信号
ignore:@2] //忽略为 2 的值
ignore:@3] //忽略为 3 的值
subscribeNext:^(NSNumber *x) {
NSLog(@"%@",x);
} completed:^{
NSLog(@"%@",@"done");
}];
Result:
2017-08-22 10:09:18.975972+0800 ReactiveCocoaDemo[474:94852] 1
2017-08-22 10:09:18.977223+0800 ReactiveCocoaDemo[474:94852] 4
2017-08-22 10:09:18.977714+0800 ReactiveCocoaDemo[474:94852] 5
2017-08-22 10:09:18.978108+0800 ReactiveCocoaDemo[474:94852] done
2 & 3 被忽略掉了
10、mapReplace 操作
将所有 next 事件发送的 value 全部替换成指定的 value
NSArray *numArray = @[@1, @2, @3, @4, @5];// 创建一个数字数组
[[[numArray.rac_sequence signalWithScheduler:RACScheduler.mainThreadScheduler] //序列转为信号
mapReplace:@10] // 全部替换为10
subscribeNext:^(NSNumber *x) {
NSLog(@"%@",x);
} completed:^{
NSLog(@"%@",@"done");
}];
Result:
2017-08-22 10:11:28.525898+0800 ReactiveCocoaDemo[479:95690] 10
2017-08-22 10:11:28.526540+0800 ReactiveCocoaDemo[479:95690] 10
2017-08-22 10:11:28.526869+0800 ReactiveCocoaDemo[479:95690] 10
2017-08-22 10:11:28.527160+0800 ReactiveCocoaDemo[479:95690] 10
2017-08-22 10:11:28.527446+0800 ReactiveCocoaDemo[479:95690] 10
2017-08-22 10:11:28.527875+0800 ReactiveCocoaDemo[479:95690] done