2013-09-05 14 views
1

我的應用程序旨在查看產品目錄的產品。從服務器(xml)接收的所有數據都在NSDictionary中解析。所以NSDictionary包含大約5000個項目。使用NSKeyedUnarchiver讀取字典需要24秒。這是不可接受的。節約大量的NSDictionary到磁盤的iOS

我並不需要向前和向後兼容的,因爲應用程序後更新目錄將重新下載和舊的數據將被刪除。

我的字典不是財產清單,所以將writeToFile不工作。

NSArchiever(NSUnarchiever)將是一個偉大的解決問題的方法,但它通過的NSKeyedArchiver取代。

任何想法?也許我應該使用CoreData,但我對此一無所知。

感謝

+1

你爲什麼不只是使用一個SQLite數據庫保存,多數民衆贊成在手機上? – heinst

回答

0

你試過將其保存爲一個JSON格式的文件? NSJSONSerialization將幫助你在文件數據和NSDictionary之間來回切換。它是在iOS5中添加的。

https://developer.apple.com/library/ios/documentation/Foundation/Reference/NSJSONSerialization_Class/Reference/Reference.html

讓我知道,如果它執行不夠好爲您服務。

+0

謝謝你的建議。但我的字典的鍵是NSNumber(它是產品ID)的實例,它不能轉換爲JSON。 – maxibystro

+0

你有沒有試過把密鑰存儲爲這些數字的字符串表示?如果你真的不需要他們成爲數字,它可能會起作用。 – veducm

+0

這就是我現在正在做的)但是,也許這是錯誤的做法。 – maxibystro

-1

我解決方案是使用自定義序列化。最後,所有數據都以屬性列表形式呈現。應序列化支持協議PropertyListCoder(如NSCoder)我所有的自定義類:

@protocol PropertyListCoder 

- (id)encodeToPropertyListObject; 
- (id)initWithPropertyListObject:(id)object; 

@end 

例如,序列化類產品:

@interface Product : NamedObject <NSCoding, PropertyListCoder> { 
} 

@property (nonatomic, readwrite) uint    mId; 
@property (nonatomic, retain) NSString    *mDesc; 
@property (nonatomic, retain) NSString    *mIcon; 

@property (nonatomic, retain) NSString    *mCode; 
@property (nonatomic, readwrite) uint    mSort; 
@property (nonatomic, retain) NSMutableArray  *mArrOfText; 

@property (nonatomic, readonly) NSMutableArray  *mProperties; 
@property (nonatomic, retain) NSString    *mImage; 
@property (nonatomic, readwrite) float    mPrice; 
@property (nonatomic, readwrite) float    mDiscPrice; 

@end 

這裏是該協議的方法:

- (id)encodeToPropertyListObject { 
id superPropList = [super encodeToPropertyListObject]; 
NSNumber* idNumber = [[NSNumber alloc] initWithInt:mId]; 
NSNumber* sortNumber = [[NSNumber alloc] initWithInt:mSort]; 
NSMutableArray* arrOfTextPropList = [[NSMutableArray alloc] init]; 
for (NSAttString* str in self.mArrOfText) { 
    [arrOfTextPropList addObject:[str encodeToPropertyListObject]]; 
} 
NSMutableArray* propPropList = [[NSMutableArray alloc] init]; 
for (Property* prop in self.mProperties) { 
    [propPropList addObject:[prop encodeToPropertyListObject]]; 
} 
NSNumber* priceNumber = [[NSNumber alloc] initWithInt:mPrice]; 
NSNumber* discPriceNumber = [[NSNumber alloc] initWithInt:mDiscPrice]; 

NSArray* res = [NSArray arrayWithObjects:superPropList, idNumber, [Utility notNilStringWithString:mDesc], [Utility notNilStringWithString:mIcon], [Utility notNilStringWithString:mCode], sortNumber, arrOfTextPropList, propPropList, [Utility notNilStringWithString:mImage], priceNumber, discPriceNumber, nil]; 

[idNumber release]; 
[sortNumber release]; 
[arrOfTextPropList release]; 
[propPropList release]; 
[priceNumber release]; 
[discPriceNumber release]; 

return res; 
} 

- (id)initWithPropertyListObject:(id)object { 
NSArray* arr = (NSArray*)object; 
self = [super initWithPropertyListObject:[arr objectAtIndex:0]]; 
if (self) { 
    mId = [[arr objectAtIndex:1] intValue]; 
    mDesc = [[arr objectAtIndex:2] retain]; 
    mIcon = [[arr objectAtIndex:3] retain]; 
    mCode = [[arr objectAtIndex:4] retain]; 
    mSort = [[arr objectAtIndex:5] intValue]; 
    mArrOfText = [[NSMutableArray alloc] init]; 
    mProperties = [[NSMutableArray alloc] init]; 

    for (id subObj in (NSArray*)[arr objectAtIndex:6]) { 
     NSAttString* str = [[NSAttString alloc] initWithPropertyListObject:subObj]; 
     [mArrOfText addObject:str]; 
     [str release]; 
    } 
    for (id subObj in (NSArray*)[arr objectAtIndex:7]) { 
     Property* prop = [[Property alloc] initWithPropertyListObject:subObj]; 
     [mProperties addObject:prop]; 
     [prop release]; 
    } 
    mImage = [[arr objectAtIndex:8] retain]; 
    mPrice = [[arr objectAtIndex:9] floatValue]; 
    mDiscPrice = [[arr objectAtIndex:10] floatValue]; 
} 
return self; 
} 

根對象可能是NSDictionary或NSArray。然後爲了讀/寫,我使用二進制格式的NSPropertyListSerialization。 現在閱讀詞典需要3.5秒!