我希望至少有兩個數組,我可以在用戶第一次保存某些內容時創建,然後在用戶想要查看該數據時從數組讀取數據並更新用戶完成更新時的數據。當應用程序運行時保存和加載數據
是否需要手動創建文件或者在運行時如何在設備上完成此操作?
只需將設備上的2個陣列以正確的路徑存儲在設備上,並在需要時加載/更新。我嘗試了一些東西,但似乎沒有得到它的工作。
我希望至少有兩個數組,我可以在用戶第一次保存某些內容時創建,然後在用戶想要查看該數據時從數組讀取數據並更新用戶完成更新時的數據。當應用程序運行時保存和加載數據
是否需要手動創建文件或者在運行時如何在設備上完成此操作?
只需將設備上的2個陣列以正確的路徑存儲在設備上,並在需要時加載/更新。我嘗試了一些東西,但似乎沒有得到它的工作。
我強烈建議使用某種數據庫來保存這些數據,無論是核心數據還是SQLite。使用SQLite(我的強項),您可以保持數據庫文件處於打開狀態,並以事務方式保存對數組的更改。由於SQLite的journalling mechanism及其驚人的深入testing regime,發生任何錯誤的可能性非常小。核心數據建立在SQLite之上,所以適用相同的保證。
編輯(RE:評論):
矯枉過正只有在情況下一個問題,即對正在解決的問題的解決方案的成本過高。 SQLite只是坐在要求使用。首先,你可以創建一個數據結構來更有意義表示數據:
@interface Memo {
NSString *title;
NSString *textBody;
};
@property (nonatomic, retain) title;
@property (nonatomic, retain) textBody;
@end
@implementation Memo
@synthesize title, textBody;
@end
的SQLite的原始界面有點笨重,所以我會保存這些使用C++ wrapper library讓事情變得簡單加載:
- (NSString *)databasePath {
NSArray *documentPaths = NSSearchPathForDirectoriesInDomains(NSDocumentDirectory, NSUserDomainMask, YES);
NSString *documentsDir = [documentPaths objectAtIndex:0];
// Choose a filename for your database.
return [documentsDir stringByAppendingPathComponent:@"data.db"];
}
- (void)saveMemos:(NSArray *)memos {
try {
sqlite3_connection con([[self databasePath] cStringUsingEncoding:NSUTF8StringEncoding]);
con.executenonquery("CREATE TABLE IF NOT EXISTS memo (i, title, textBody)");
sqlite3_transaction trans(con);
{
sqlite3_command cmd(con,
"INSERT INTO memo (i, title, textBody) VALUES (?, ?, ?)");
for (int i = 0; i < memos.count; i++) {
Memo *memo = (Memo *)[memos objectAtIndex:i];
cmd.bind(1, i);
cmd.bind(2, [memo.title cStringUsingEncoding:NSUTF8StringEncoding]);
cmd.bind(3, [memo.textBody cStringUsingEncoding:NSUTF8StringEncoding]);
cmd.executenonquery();
}
}
trans.commit();
} catch(exception &ex) {
NSLog(@"SQLite3 error: %s", ex.what());
}
}
- (NSMutableArray *)loadMemos {
sqlite3_connection con([[self databasePath] cStringUsingEncoding:NSUTF8StringEncoding]);
NSMutableArray *result = [NSMutableArray arrayWithCapacity:10];
if (con.executeint("SELECT COUNT(*) FROM sqlite_master WHERE name = 'memo'")) {
sqlite3_command cmd("SELECT title, textBody FROM memo ORDER BY i");
sqlite3_reader rd = cmd.executereader();
while (rd.read()) {
Memo *memo = [[Memo alloc] init];
memo.text = [NSString stringWithFormat:@"%s", rd.getstring(0).c_str()];
memo.titleBody = [NSString stringWithFormat:@"%s", rd.getstring(1).c_str()];
[result addObject:memo];
}
}
return result;
}
(警告:此代碼是完全未經測試)
這是不可能一個土生土長的文件格式將需要比這更少的代碼,它幾乎肯定會不太可靠。
你也應該考慮核心數據,但我自己並沒有使用它,所以我不能在這方面提供幫助。
假設有一個筆記/備忘錄,每個備忘錄都有一個標題和一個文本正文。我創建一個字符串作爲title^textBody並將該字符串添加到數組中。這個數組需要存儲在某個地方(每添加一個新註釋之後,數組必須被更新和保存,當程序啓動時需要讀取數組,以便用戶可以看到他們保存的註釋。這個少量的數據,這個數組怎麼能夠在運行時保存更多的字符串數組,我試圖寫入plist,但是它在應用程序退出之後從未存儲過數據 – jarryd 2010-07-13 10:22:38
「overkill」是什麼意思? – 2010-07-13 10:33:11
I不認爲有必要爲2個數組實現一個數據庫?但我不知道,我不知道如何做到這一點。如何存儲2個數組?我已閱讀NSKeyedArchiver,但不知道如何實現它。 – jarryd 2010-07-13 10:49:47
如果你的數據是NS *數據結構,比如NSDictionary或者NSArray,NSUserDefaults真的很容易實現持久化數據。如果你的數據不是很大,那麼使用NSUserDefaults是最好的選擇。我通常會創建一個「保存」方法,我從我稱之爲從application:didFinishLaunchingWithOptions:
#define kThing1Key @"thing1"
#define kThing2Key @"thing2"
...
- (void) save
{
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
[defaults setObject:self.thing1 forKey:kThing1Key];
[defaults setObject:self.thing2 forKey:kThing2Key];
...
[defaults synchronize];
}
- (void) load
{
NSUserDefaults *defaults = [NSUserDefaults standardUserDefaults];
self.thing1 = [defaults objectForKey:kThing1Key];
self.thing2 = [defaults objectForKey:kThing2Key];
...
}
這個問題是非常困難的閱讀應用程序委託的
applicationWillTerminate,
和負載方法調用。例如,什麼,「我想有2個或至少2個陣列......」是什麼意思? – 2010-07-13 10:06:06編輯。 :)謝謝 – jarryd 2010-07-13 10:24:03