Ash*_*row 11 objective-c reactive-programming ios reactive-cocoa
尝试遵循ReactiveCocoa 的最佳实践,每小时更新我的UI.这就是我所拥有的:
NSDateComponents *components = [[[NSCalendar sharedCalendar] calendar] components:NSMinuteCalendarUnit fromDate:[NSDate date]];
// Generalization, I know (not every hour has 60 minutes, but bear with me).
NSInteger minutesToNextHour = 60 - components.minute;
RACSubject *updateEventSignal = [RACSubject subject];
[updateEventSignal subscribeNext:^(NSDate *now) {
// Update some UI
}];
[[[RACSignal interval:(60 * minutesToNextHour)] take:1] subscribeNext:^(id x) {
[updateEventSignal sendNext:x];
[[RACSignal interval:3600] subscribeNext:^(id x) {
[updateEventSignal sendNext:x];
}];
}];
Run Code Online (Sandbox Code Playgroud)
这有一些明显的缺陷:手动订阅和发送,只是"感觉不对劲".关于如何使这更"反应"的任何想法?
Jus*_*ers 20
您可以使用完全香草运算符来完成此操作.这只是将两个区间链接在一起同时仍然通过它们的两个值的问题,这正是-concat:的作用.
我会按如下方式重写这个主题:
RACSignal *updateEventSignal = [[[RACSignal
interval:(60 * minutesToNextHour)]
take:1]
concat:[RACSignal interval:3600]];
Run Code Online (Sandbox Code Playgroud)
这可能无法为您提供超精确的精确度(因为两个信号之间可能存在微小的打嗝),但对于任何UI工作而言应该是Good Enough™.
听起来你需要类似的东西+interval:startingIn:
.
有了这个想法,你可以+interval:startingIn:
通过略微调整实现+interval:
来制作你自己的版本.
+ (RACSignal *)interval:(NSTimeInterval)interval startingIn:(NSTimeInterval)delay {
return [[RACSignal createSignal:^(id<RACSubscriber> subscriber) {
int64_t intervalInNanoSecs = (int64_t)(interval * NSEC_PER_SEC);
int64_t delayInNanoSecs = (int64_t)(delay * NSEC_PER_SEC);
dispatch_source_t timer = dispatch_source_create(DISPATCH_SOURCE_TYPE_TIMER, 0, 0, dispatch_get_global_queue(DISPATCH_QUEUE_PRIORITY_HIGH, 0));
dispatch_source_set_timer(timer, dispatch_time(DISPATCH_TIME_NOW, delayInNanoSecs), (uint64_t)intervalInNanoSecs, (uint64_t)0);
dispatch_source_set_event_handler(timer, ^{
[subscriber sendNext:[NSDate date]];
});
dispatch_resume(timer);
return [RACDisposable disposableWithBlock:^{
dispatch_source_cancel(timer);
dispatch_release(timer);
}];
}] setNameWithFormat:@"+interval: %f startingIn: %f", (double)interval, (double)delay];
}
Run Code Online (Sandbox Code Playgroud)
有了这个,您的代码可以重构为:
NSDateComponents *components = [[[NSCalendar sharedCalendar] calendar] components:NSMinuteCalendarUnit fromDate:[NSDate date]];
// Generalization, I know (not every hour has 60 minutes, but bear with me).
NSInteger minutesToNextHour = 60 - components.minute;
RACSubject *updateEventSignal = [[RACSignal interval:3600 startingIn:(minutesToNextHour * 60)];
[updateEventSignal subscribeNext:^(NSDate *now) {
// Update some UI
}];
Run Code Online (Sandbox Code Playgroud)
归档时间: |
|
查看次数: |
2974 次 |
最近记录: |