2012-02-08 4 views
20

Sau đây là trong file .h của tôi:Khởi tạo NSDictionary

NSDictionary *originalValues; 
    @property (nonatomic, retain) NSDictionary *originalValues; 

Đây là tập tin .m để init NSDictionary.

@synthesize originalValues; 

- (void)viewDidLoad { 

// copy original values when view loaded 
originalValues = [[NSDictionary alloc] initWithObjectsAndKeys:place.city, @"city", place.cuisine, @"cuisine", 
       place.latitude, @"latitude", place.longitude, @"longitude", place.name, @"name", place.rating, 
       @"rating", place.state, @"state", place.street, @"street", place.telephone, @"telephone", 
       place.timesVisited, @"times visited", place.uppercaseFirstLetterOfName, @"first letter", 
       place.website, @"website", place.zipcode, @"zipcode", nil]; 
} 

Vấn đề chỉ là bốn đối tượng và phím đầu tiên được thêm vào. Sau đó, chúng không được thêm vào từ điển bắt đầu bằng place.name, @ "name". Tôi đã làm một NSLog trên toàn bộ từ điển và những thứ duy nhất được xuất ra là bốn giá trị đầu tiên như tôi đã đề cập, sau đó II đã làm một NSLog trên place.name và nó xuất ra một giá trị vì vậy tôi biết điều gì đó cũng nên được xuất ra cho khóa/giá trị này đôi. Có điều gì tôi thiếu ở đây không? Tôi tò mò tại sao tất cả các giá trị không được thêm vào NSDictionary ban đầu?

Trả lời

43

Lý do tại sao chúng không được thêm vào là do đối tượng là số không đánh dấu sự kết thúc của từ điển. Bạn cần đảm bảo rằng mỗi đối tượng không phải là nil và nếu bạn có thể sử dụng [NSNull null] thay cho đối tượng đó. Cũng sử dụng self.originalValues = ... để quản lý bộ nhớ phù hợp. Chỉ cần đảm bảo những gì từng sử dụng kiểm tra từ điển/có thể xử lý các giá trị NSNull.

Ví dụ sử dụng gnu ternary extension:

self.originalValues = [[NSDictionary alloc] initWithObjectsAndKeys: 
         place.city ?: [NSNull null], @"city", 
         place.cuisine ?: [NSNull null], @"cuisine", 
         place.latitude ?: [NSNull null], @"latitude", 
         place.longitude ?: [NSNull null], @"longitude", 
         place.name ?: [NSNull null], @"name", 
         place.rating ?: [NSNull null], @"rating", 
         place.state ?: [NSNull null], @"state", 
         place.street ?: [NSNull null], @"street", 
         place.telephone ?: [NSNull null], @"telephone", 
         place.timesVisited ?: [NSNull null], @"times visited", 
         place.uppercaseFirstLetterOfName ?: [NSNull null], @"first letter", 
         place.website ?: [NSNull null], @"website", 
         place.zipcode ?: [NSNull null], @"zipcode", 
         nil]; 
+2

@TReddy Tôi tránh biểu thức bậc ba trong tất cả mã C và C++ của mình. Nhưng vì đây là mục tiêu-c mà thường chỉ được biên dịch bằng gcc hoặc llvm của Apple, tôi thấy không có vấn đề gì khi sử dụng nó. – Joe

54

Nếu một trong những đối tượng là nil, bạn có thể bắt mà nhanh hơn nhiều nếu bạn sử dụng cú pháp theo nghĩa đen mới cho khởi tạo một NSDictionary (dưới đây). Cú pháp này không chỉ ngắn hơn, mà còn mạnh mẽ hơn: bạn sẽ thực sự gặp phải lỗi thời gian chạy nếu một trong các đối tượng của bạn là nil, thay vì thực thi liên tục âm thầm với dữ liệu không đầy đủ.

originalValues = @{ @"city"  : place.city, 
        @"latitude" : place.latitude, 
        // etc. 
        }; 
+0

Trong khi cú pháp chữ đẹp hơn và ưa thích hơn, tôi không chắc OP đang tìm lỗi thời gian chạy khi một giá trị là 'nil'. – Joe

0

Để tránh con số không ngẫu nhiên trong bất kỳ từ điển giải pháp tốt nhất là nếu bạn kết hợp hai ngăn split gia sử dụng theo nghĩa đen và các nhà điều hành ternary như

self.originalValues = @{ @"city" : (place.city ?: @"city"), 
         @"latitude" : (place.latitude ?: [NSNull null]), 
         // etc. 
         }; 

Lưu ý:

(anyValueOrVariable?: @ "anyOtherValueOrVariable")

là một sự viết tắt và có nghĩa là giống như

(anyValueOrVariable! = 0)? anyValueOrVariable: @ "anyOtherValueOrVariable"