2014-10-02 62 views
1

好的,我有發送時的協議的某些方法被調用響應於某些數據從服務器獲取檢索的事件的信號:ReactiveCocoa:手動發送事件

self.dataReceivedSignal = [[self rac_signalForSelector:@selector(didReceiveData:) fromProtocol:@protocol(DataServiceDelegate)] mapReplace:@YES]; 

該信號然後用於消防另一個信號格式,並返回數據:

- (RACSignal *)dataSignal 
{ 
    return [RACSignal combineLatest:@[self.dataReceivedSignal] reduce:^id(NSNumber * received){ 
     ... 
     return my_data; 
    }]; 
} 

此視圖控制器只是聽這個第二信號來獲取數據。

這工作正常。

問題是,我進入這個視圖控制器第二次,我不想再加載數據,所以我將它保存在本地,並做到這一點:

if (!self.alreadyHasData) { 
    self.dataService = [[DataService alloc] init]; 
    self.dataService.delegate = self; 
    [self.dataService getData]; 
} else { 
    self.dataReceivedSignal = [RACSignal return:@YES]; 
} 

如果我已經有數據,我用一個只發送@YES並完成的新數據替換dataReceivedSignal。

這也適用,但是如果/ else對我來說似乎不太實用。這是正確的方法嗎?

謝謝。

回答

0

首先您可以兌換combineLatestmap。 如果,如果它已經加載要的不是重新加載數據,你可以寫這樣的事情:

- (RACSignal *)dataSignal 
{ 
    if (!_dataSignal) { 
     RACMulticastConnection *dataConnection = [[self.dataReceivedSignal map:^id(NSNumber * received){ 
      /// ... 
      return my_data; 
     }] multicast:[RACReplaySubject replaySubjectWithCapacity:1]]; 

     // Only do all of the above after one subscriber has attached. 
     _dataSignal = [RACSignal defer:^{ 
      [dataConnection connect]; 
      return dataConnection.signal; 
     }]; 
    } 
    return _dataSignal; 
} 

不要再多的用戶信號都會有,檢索數據塊會被調用一次。

簡單的代碼=更好的代碼。我認爲你可以在沒有RAC的情況下用更簡單的解決方案解決任務

+0

有些東西不行:subscribeNext的塊不應該返回任何東西。而且subscribeNext調用返回一個RACDisposable(不是RACSignal),所以它不能多播。 – Odrakir 2014-10-02 10:58:19

+0

對不起,很久沒有用過RAС了。我更新了答案,將subscribe改爲映射。我已經測試過代碼,現在看來這種模式必須適合你。 – Sk0prion 2014-10-03 07:47:34

+0

對不起,但我還是不明白。我在哪裏放我的DataService代碼呢? – Odrakir 2014-10-06 09:12:09