28

Tôi có một từ điển các đối tượng; chúng là tất cả các đối tượng POCO cần được tuần tự hóa. Tôi nên xem xét kỹ thuật nào để viết những cái này lên đĩa. Tôi đang tìm kiếm tùy chọn đơn giản nhất để viết một vài danh sách để lưu trạng thái.Làm cách nào để tuần tự hóa một đối tượng đơn giản trong sdk iPhone?

Tôi nghĩ mình có 3 tùy chọn.

  1. tệp plist. Tuy nhiên điều này dường như bị giới hạn chỉ lưu trữ các đối tượng được xác định trước (chuỗi, số, vv) không phải đối tượng (như một người có tên và tuổi).

  2. CoreData. (Mới trong 3.0) Điều này sẽ làm việc tốt; tuy nhiên mô hình dữ liệu của tôi sẽ cần phải thay đổi để thực hiện công việc này. Đây sẽ là một bản làm lại lớn và tôi không chắc liệu nó có đáng để nỗ lực không.

  3. SQLLite. Thực hiện một cơ sở dữ liệu SQL đơn giản để đọc đến và đi. Tôi đã thực hiện số tiền ít nhất của reserch vào này, nhưng tôi không muốn phải 'viết lại' một số chức năng ORM dữ liệu cốt lõi.

Trả lời

14

Bạn làm điều này giống như cách bạn thực hiện trên Mac OS X: POCO của bạn phải tuân theo giao thức NSCoding. Xem here để tham khảo khái niệm và here để tham chiếu NSCoding.

Nếu dữ liệu không quá điên rồ và bạn không có mối quan hệ phức tạp vô lý giữa các đối tượng của bạn, hãy viết mọi thứ ra ngoài như một plist có lẽ là lựa chọn tốt nhất của bạn; nó rất nhanh để thực thi và thực hiện đơn giản trong mã của bạn. Như bạn đã nói, CoreData có thể sẽ là lot công việc bổ sung để thích ứng với mã của bạn và sqlite thực sự chỉ tốt để lưu trữ dữ liệu hoàn hảo để lưu trữ trong cơ sở dữ liệu quan hệ. Hãy nhớ rằng sqlite cũng chậm hơn và sử dụng nhiều tài nguyên hơn là làm việc với các plist nhị phân.

33

Để tuần tự hóa đối tượng tùy chỉnh, bạn chỉ cần tuân thủ giao thức NSCoding. Nếu đối tượng của bạn kéo dài NSObject tất cả các bạn cần làm (Tôi tin) là thực hiện này (ví dụ cho đối tượng người):

// Encode an object for an archive 
- (void)encodeWithCoder:(NSCoder *)coder 
{ 
    [super encodeWithCoder:coder]; 
    [coder encodeObject:name forKey:@“Name”]; 
    [coder encodeInteger:age forKey:@“Age”]; 
} 
// Decode an object from an archive 
- (id)initWithCoder:(NSCoder *)coder 
{ 
    self = [super initWithCoder:coder]; 
    name = [[coder decodeObjectForKey:@“Name”] retain]; 
    age = [coder decodeIntegerForKey:@“Age”]; 
} 

NSArrayNSDictionary đã thực hiện phương pháp serialization. Họ sẽ tuần tự hóa tất cả các đối tượng mà họ nắm giữ (nếu các đối tượng thực hiện giao diện NSCoder - họ thực hiện nếu họ mở rộng NSObject). NSObject's encodeWithCoderinitWithCoder không làm gì theo mặc định, trừ khi bạn triển khai mã của riêng bạn trong lớp học của bạn, không có thứ gì được đăng.

Nếu bạn có NSArray hoặc NSDictionary của các đối tượng, bạn có thể đồng bộ hóa chúng bằng cách sử:

// Writing 
- (BOOL)writeToFile:(NSString *)aPath atomically:(BOOL)flag; 
- (BOOL)writeToURL:(NSURL *)aURL atomically:(BOOL)flag; 
// Reading 
- (id)initWithContentsOfFile:(NSString *)aPath; 
- (id)initWithContentsOfURL:(NSURL *)aURL; 
+0

tên là đối tượng của loại NSString do đó bạn muốn giữ lại nếu bạn muốn sử dụng nó, tuổi tác chỉ là nguyên thủy nguyên – stefanB

+0

Bạn có thể không sử dụng writeToFile, writeToURL trừ khi các đối tượng trong NSArray có kiểu NSString, NSData, NSArray hoặc NSDictionary. Nó sẽ luôn trả về NO nếu bạn cố gắng sử dụng các phương thức này trên một NSArray với bất kỳ kiểu đối tượng nào khác. – Snickers

+0

@Snickers bạn đang nói về NSArray đầy đủ các loại đối tượng khác mà tất cả thực hiện giao thức 'NSCoding'? Bởi vì đó là những gì tôi đã giải thích ở trên. Nếu không, không chắc chắn, đó là câu trả lời 3 tuổi, công cụ có thể đã thay đổi, xin vui lòng gửi câu trả lời của bạn ppl sẽ upvote nếu nó là giải pháp tốt hơn. – stefanB

Các vấn đề liên quan