2010-09-04 73 views
11

有誰知道如何在應用程序啓動之間將NSOperationQueue持久化到磁盤?堅持NSOperationQueue

+0

您能告訴我們您想要達到的目標嗎?也許有更好的方法來解決你的問題比堅持NSOperationQueue。 – hwaxxer 2012-05-24 08:04:08

回答

10

沒有辦法這樣做。 NSOperations是行爲,可運行代碼的一部分,不可能一般持久化到磁盤。

但是,在您的應用程序中,您應該知道您添加到隊列中的操作。無論是通過使用一個子類或有一些元數據。然後,您將以自定義的方式存儲元數據以及應該完成的信息。在啓動應用程序後,現在可以從加載的元數據重新創建以前在隊列中的操作。

目前幾乎沒有其他的東西可以給你,但是我希望這對你有幫助!

5

我同意Max - 沒有一個通用的方法來做到這一點。通常情況下,您希望使操作在概念上處於事務狀態並與有限狀態機中的狀態關聯。在每個狀態轉換(即完成的操作)上保持當前狀態和任何其他適當的數據,然後有一段代碼根據當前狀態用適當的操作填充NSOperationQueue。從您的UI驅動代碼中調用相同的代碼並重新啓動應用程序。

與我合作的團隊已經討論了一段時間儘可能多地使用這種方法的通用方法(理想的是作爲可重用的類或框架),但我們還沒有進行過很多工作。

4

如果你有一個相對簡單的隊列,在操作之間沒有依賴關係,通過利用NSCoder這應該是相當簡單的。

這樣做,這將是如下的一般方法:

  1. 迭代通過使用NSOperationQueue 操作屬性在隊列中掛起的NSOperation項目。操作將按照它們添加到隊列中的順序進行,並且您將要保留排序。

  2. 您的NSOperations應該進行分類並實施NSCoding協議,以便每個操作都知道如何使用NSArchiver進行歸檔和解除歸檔。您需要確定哪些屬性需要序列化才能正確恢復隊列的狀態。如果您創建了任何互操作依賴關係,那麼您有責任以某種方式保存和恢復這些關係 - 而且很可能,如果您的隊列以這種方式複雜,您可能不希望首先執行此操作。對操作進行序列化(歸檔),並將其存儲到NSArray或使用其他結構來保留隊列順序。

  3. 將包含序列化操作的NSArray存檔到文件中。

  4. 要恢復您的隊列,您需要從文件中「解開」NSArray,然後遍歷操作列表,將每個NSOperation解除存檔,然後將其添加到隊列中,與原始排序相關。
6

非常容易,首先要確保所有NSOperations的採用NSCoding協議,並實現方法告訴他們要保存和恢復哪些字段:

MyOperation.h

@interface MyOperation : NSOperation<NSCoding> 

MyOperation。米

#pragma mark NSCoding 

#define kSomeKey  @"someKey" 

- (void) encodeWithCoder:(NSCoder *)encoder { 
    [encoder encodeObject:[self someKey] forKey:kSomeKey]; 
} 

- (id)initWithCoder:(NSCoder *)decoder { 

    if (self = [super init]) { 
     NSString *someKey = [decoder decodeObjectForKey:kSomeKey]; 
     [self setSomeKey:someKey]; 
    } 

    return self; 
} 

最後,序列化,只要你想反序列化隊列。這會將其存儲到Documents/data文件中的手機存儲中,假設您的隊列名爲operations

NSString * const dataPath = @"~/Documents/data"; 

// private 
- (void) serializeQueue { 
    NSArray* storedOperations = [[self operations] operations]; 

    [NSKeyedArchiver archiveRootObject:storedOperations toFile:[dataPath stringByExpandingTildeInPath]]; 
} 

// private 
- (void) deserializeQueue { 
    NSArray* storedOperations = [NSKeyedUnarchiver unarchiveObjectWithFile:[dataPath stringByExpandingTildeInPath]]; 

    NSLog(@"count of opeations: %lu", (unsigned long) [storedOperations count]); 
}