2012-04-09 7 views
7

xem xét:sao chép bất động sản và Block_copy (myBlock)/[myBlock bản sao]

typedef void (^select_block_t)(UIView *) ; 

(1) @property (copy, nonatomic) select_block_t  myBlockProperty ; 
(2) @property (strong, nonatomic) select_block_t  myBlockProperty ; 
(3) @property (assign, nonatomic) select_block_t  myBlockProperty ; 

và:

(A) self.myBlockProperty = ^(UIView *) {NSLog(@"Hi");} ; 
(B) self.myBlockProperty = [^(UIView *) {NSLog(@"Hi");} copy] ; 

Tôi cố gắng để hiểu được cách chính xác để lập bản đồ mà kê khai tài sản là những gì mà ngữ nghĩa bản sao khối

Tôi đã xem các ví dụ here trên S.O. có lợi cho [1: B]

Nhưng sau đó tôi bị lẫn lộn bởi cách hoạt động dự phòng 'sao chép' dư thừa. Hiểu biết hạn chế của tôi là [1: A] phải chính xác, vì tôi muốn khối sẽ được sao chép một lần khi tôi chỉ định thuộc tính, không phải lúc tạo khối và sau đó một lần nữa tại thời điểm gán thuộc tính.

[3: B] cũng sẽ có ý nghĩa theo lý do cơ bản của tôi. Vì vậy, tôi hiểu lầm gì?

Trả lời

9

[1: A] là đúng, có. [3: B] là không đúng vì:

  1. nó không phải là rõ ràng rằng lớp sở hữu tài sản, vì vậy nên thả nó trong dealloc (nhưng nó nên)
  2. setter (B) trông giống như một rò rỉ, và máy phân tích tĩnh có thể gắn cờ nó như vậy, bởi vì khối được sao chép, giao cho một tài sản, sau đó rời khỏi phạm vi với số lượng giữ lại +1.
  3. sử dụng (3) có nghĩa là nó chỉ hoạt động nếu bạn đặt khối heap (khối sao chép) có số lượng giữ lại là một. Điều này để lại rất nhiều lỗi khi sử dụng thuộc tính. (1) hoạt động với cả khối ngăn xếp và khối heap, và cũng sẽ giữ nguyên các khối tự động giải phóng một cách chính xác.

EDIT: Tôi thấy bạn đang sử dụng ARC. Trong trường hợp đó, hoàn toàn không thể sử dụng [3: B]. Trình biên dịch sẽ phát hành một đối tượng (ngay cả khi copy ed) một khi nó nằm ngoài phạm vi, và thiết lập thuộc tính này sẽ không giữ lại nó. Do đó thuộc tính sẽ chứa một con trỏ xấu, đó là một EXC_BAD_ACCESS đang chờ xảy ra.

+0

Chờ, bạn vừa thấy thẻ của mình _automatic-ref-counting_, bạn có đang sử dụng ARC không? – joerick

+0

Có, tôi đang sử dụng ARC. – verec

+0

@verec Tôi đã cập nhật câu trả lời của mình. Hãy cho tôi biết nếu bạn có bất kỳ câu hỏi nào, tôi không chắc tôi đã rõ ràng như thế nào! – joerick