2008-10-09 39 views
28

Có thực hành tốt để thực hiện xử lý sự kiện thông qua WeakReference nếu sự kiện đó là điều duy nhất giữ tham chiếu và rằng chúng ta sẽ cần đối tượng được thu gom rác?WeakReference và xử lý sự kiện

Như một cuộc tranh cãi như thế này:

Folks nói rằng nếu bạn đăng ký vào một cái gì đó nó là trách nhiệm của bạn để bỏ đăng ký và bạn nên làm điều đó.

+0

Câu hỏi trở thành: Cơ hội nào mà sự kiện đó được kích hoạt vào lúc đối tượng thu thập rác? Tại sao sử dụng một WeakReference ở nơi đầu tiên? –

+0

@Jon Limjap mà không có một sự suy yếu, không phải là cơ hội số không vì sự kiện giữ một ca khúc của đối tượng và do đó nó sẽ không được thu thập? – fostandy

+0

@fostandy: Không, nhà xuất bản của một sự kiện sẽ không bị người đăng ký giữ lại, nó chỉ hoạt động theo cách khác. Để cho phép người đăng ký được GC'ed mà không phải hủy đăng ký trước, người dùng nên sử dụng WeakReference. Xem: http://stackoverflow.com/a/298276/134761 – angularsen

Trả lời

-2

Trong khi những gì bạn đề xuất giải quyết một tập hợp các vấn đề (quản lý tham chiếu sự kiện và phòng chống rò rỉ bộ nhớ), nó có khả năng mở ra một tập hợp các vấn đề mới. Một vấn đề tôi có thể thấy là trong quá trình xử lý sự kiện nếu đối tượng nguồn là rác được thu thập (vì nó chỉ được giữ với tham chiếu yếu), bất kỳ mã nào truy cập đối tượng nguồn sẽ dẫn đến ngoại lệ tham chiếu null. Bạn có thể tranh luận rằng trình xử lý sự kiện không nên truy cập đối tượng nguồn hoặc nó phải có tham chiếu mạnh mẽ, nhưng có thể lập luận rằng đây có thể là vấn đề tồi tệ hơn vấn đề bạn đang cố giải quyết ngay từ đầu.

+1

Khi CLR đã thực hiện xử lý sự kiện, ngăn xếp sẽ giữ tham chiếu đến "điều này" và các đối tượng sẽ không được thu thập. –

9

Mẫu ủy nhiệm yếu là thứ cần có trong CLR. Sự kiện bình thường thể hiện "thông báo cho tôi khi bạn còn sống" ngữ nghĩa, trong khi thường chúng ta cần "thông báo cho tôi khi tôi còn sống". Chỉ cần có đại biểu trên WeakReference là sai, bởi vì đại biểu là một đối tượng quá và ngay cả khi người nhận vẫn còn sống và có tài liệu tham khảo đến, đại biểu chính nó chỉ được tham chiếu bởi WeakReference nói và sẽ được thu thập ngay lập tức. Xem this old post để biết ví dụ về triển khai.

6

Tham chiếu yếu theo cách riêng của chúng, không giải quyết được sự cố khi đại biểu giữ tham chiếu. Trong thư viện ứng dụng tổng hợp mà tàu với Prism (www.microsoft.com/compositewpf) có một lớp WeakDelegate mà bạn có thể kéo từ nguồn. Các WeakDelegate về cơ bản ues phản ánh và tạo ra một đại biểu chỉ cho một thời điểm trong thời gian và sau đó phát hành nó, do đó không giữ bất kỳ con trỏ. Trong CAL nó được sử dụng bởi lớp EventAggregator, nhưng bạn có thể tự do tách nó ra để sử dụng cho chính bạn vì nó nằm dưới MS-PL.

13

Bạn nên có thói quen hủy đăng ký các sự kiện khi có thể, nhưng đôi khi không có phương pháp "dọn sạch" rõ ràng ở nơi có thể thực hiện. Gần đây, chúng tôi đã đăng một số blog article về chủ đề này; nó bao gồm các phương thức giúp dễ dàng đăng ký một sự kiện với một WeakReference.

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