7

Tôi có hai khối GCD không đồng bộ. Đầu tiên là chủ đề nền, chuỗi thứ hai chạy trên luồng chính. Điều này làm việc tuyệt vời, nhưng tôi chỉ thấy một nơi nào đó nói rằng tôi có thể cần phải giải phóng chúng bằng cách sử dụng dispatch_release(). Ví dụ:dispatch_queue_t cần được phát hành bằng dispatch_release()?

// Use gcd 
dispatch_queue_t queue = dispatch_queue_create("com.awesome", 0); 
dispatch_queue_t main = dispatch_get_main_queue(); 

// do the long running work in bg async queue 
// within that, call to update UI on main thread. 
dispatch_async(queue, ^{ 
    // Do work in the background 



    // Release 
    dispatch_release(queue); 

    dispatch_async(main, ^{ 

     // Main 


     // Release 
     dispatch_release(main); 

    });//end 
});//end 

Điều này có đúng không? Tôi có cần giải phóng chúng ở đây không?

+0

Mỗi nhận xét trong tệp tiêu đề bạn cần gọi dispatch_release() trên bất kỳ hàng đợi nào bạn tạo. – BonanzaDriver

Trả lời

8

Chỉ các hàng đợi phát hành mà bạn tạo; không phát hành hàng đợi chính hoặc hàng đợi đồng thời toàn cầu (hoặc, một lần nữa, bất kỳ hàng nào bạn không tự tạo). Nó cũng không phải là một ý tưởng tốt để làm tổ phát hành trong khối công việc enqueued trên hàng đợi đó, như bạn đang làm, bởi vì đó là làm nó trong phạm vi sai và điều này:

queue = dispatch_queue_create(...) 
dispatch_async(queue, ^{ something; dispatch_release(queue); }); 
dispatch_async(queue, ^{ something else}); // CRASH! 

Sẽ không hoạt động khi bạn sau này thay đổi mã để thêm vào đó dispatch_async(). Luôn ghép nối các cuộc gọi tạo/phát hành của bạn trong cùng một phạm vi, giả sử rằng bạn có thể, là một lựa chọn phong cách tốt hơn.

+0

Ok, vì vậy tôi chỉ cần phát hành nó bên ngoài cuộc gọi dispatch_asynch? –

+0

Có. Cụ thể, bạn cần phải làm điều đó trong phạm vi tương tự như tạo cuộc gọi vì bạn thiết lập một vùng đất cho chính mình mà sau này bạn bước vào, như tôi minh họa trong câu trả lời của tôi (ngoại lệ duy nhất cho quy tắc này có thể là finalizers, nhưng chúng ta không nhầm lẫn mọi thứ :)) – jkh

13

Bạn chỉ cần giải phóng hàng đợi được tạo với dispatch_queue_create. Hàng đợi chính sẽ luôn luôn tồn tại, và nó không có ý nghĩa để phát hành nó.

Bất kỳ khối nào được thêm vào hàng đợi sẽ giữ nguyên hàng đợi, vì vậy bạn có thể gọi số dispatch_release(queue) một cách an toàn sau cuộc gọi dispatch_async của mình. Tốt nhất để làm điều này bên ngoài khối sau khi mã bạn đã viết ở đây.

+0

Ok, nhưng nếu tôi làm điều đó bên ngoài hàng đợi, nó sẽ không tự động được phát hành? –

+2

@NicHubbard Nó sẽ được phát hành khi tất cả các công việc của hàng đợi được thực hiện, ví dụ bạn có thể tạo một hàng đợi, gửi 3 - 4 khối vào nó, và giải phóng nó sau khi các cuộc gọi công văn. Hàng đợi sẽ vẫn được giữ lại cho đến khi tất cả các khối đã hoàn thành nhiệm vụ tương ứng của chúng. Tại thời điểm này bạn không còn cần hàng đợi này nữa. – Pochi

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