2011-07-10 19 views
8

Nếu tôi đang sử dụng một ManagementObjectSearcher, tôi có thể dễ dàng quấn nó trong một khối using:. Các lớp WMI Net - tôi phải loại bỏ những lớp nào?

using (var searcher = new ManagementObjectSearcher(scope, query)) 
{ 
    // ... 
} 

Nó cũng rất dễ dàng để xử lý the collection returned from the searcher, do thực tế rằng foreach automatically calls dispose on the enumerator:

using (var searcher = new ManagementObjectSearcher(scope, query)) 
{ 
    foreach(ManagementObject mo in searcher.Get()) 
    { 
     // ... 
    } 
} 

Nhưng ManagementObject cũng triển khai IDisposable:

using (var searcher = new ManagementObjectSearcher(scope, query)) 
{ 
    foreach(ManagementObject mo in searcher.Get()) 
    { 
     // ... 

     mo.Dispose(); // ? 
    } 
} 
  • Tôi có phải hủy bỏ từng trường hợp ManagementObject được trả lại trong trường hợp này không?
  • Nếu tôi làm như thế nào, làm cách nào để ngoại lệ an toàn?
  • Có cách nào tôi vẫn có thể sử dụng LINQ trong trường hợp này (và vẫn gọi đúng Dispose)? Đặc biệt với các công trình như searcher.Get().First()?

Sửa: Một số câu hỏi có liên quan:

  • Tôi cũng phải gọi Dispose vào bộ sưu tập kết quả tìm kiếm?
  • Còn người tìm kiếm thì sao?

Cả hai cũng thực hiện phương pháp IDisposable riêng của họ, mặc dù nó có vẻ như những người tìm kiếm chỉ thừa kế thực hiện Dispose từ Component; nó không thêm hành vi vứt bỏ của riêng nó.

Trả lời

3

ManagementObject được kế thừa từ System.ComponentModel.Componentyou should call Dispose explicitly cho tất cả các đối tượng được kế thừa từ Component. Bạn có thể sử dụng phương pháp LINQ với các vị từ của riêng bạn mà gọi Dispose bản thân:

var first = searcher.Get().First(x => 
       { 
        bool result = Satisfy(x); 

        if (!result) 
        { 
         x.Dispose(); 
        } 

        return result; 
       }); 

Mã này tương đương với:

ManagementObject first = null; 

foreach (var element in searcher.Get()) 
{ 
    if (Satisfy(element)) 
    { 
     first = element; 
     break; 
    } 
    else 
    { 
     element.Dispose();  
    } 
} 

if (first == null) 
{ 
    throw new InvalidOperationException("No match"); 
} 

đâu Satisfy là phương pháp riêng của mình.

+0

Xin lỗi để làm nổi bật câu hỏi của tôi sau khi bạn đã trả lời câu hỏi. Vui lòng xem các chỉnh sửa của tôi. Bạn đề cập đến các verbiage ở phía dưới mà nói rằng bạn nên luôn luôn gọi 'Dispose' trên các lớp học bắt nguồn từ' Thành phần'. Tuy nhiên, có lý do nào cho việc này đối với một lớp không thêm bất kỳ triển khai 'Vứt bỏ' nào của riêng nó không? Tôi thấy từ Reflector rằng có một số công cụ thú vị trong ruột của 'Dispose' trên' Component', nhưng nó có vẻ như nó sẽ chỉ áp dụng nếu tôi sử dụng nó trong một số loại "trang web" bối cảnh. Tôi không thể biết liệu điều đó có áp dụng trong trường hợp này hay không ... –

+0

Đã kiểm tra nó và 'Trang web 'có vẻ là rỗng. Tôi không gắn bó với on-Dispose events, do đó, nó thực sự có vẻ như nó sẽ không làm bất cứ điều gì trong trường hợp này. Nhưng tôi đánh giá cao hai xu của bạn. –

+1

Tôi nghĩ rằng các khuyến nghị phát triển khung sau đây là một thực hành tốt. Thực sự, bạn không nên sử dụng phản xạ hoặc bất kỳ điều gì khác để đưa ra bất kỳ giả định hoặc giả định nào về cách phiên bản mã hoạt động chính xác. Trong MSDN Microsoft viết rằng bạn phải gọi 'Dispose' cho mọi đối tượng được thừa kế từ' Component'. Nếu bạn không, bạn có thể gặp vấn đề trong một số trường hợp sử dụng phức tạp hoặc trong các phiên bản khác của khung công tác.Bỏ qua các thông số kỹ thuật là điều đầu tiên khiến ứng dụng không thành công trong phiên bản hệ điều hành hoặc khung công tác mới. – oxilumin

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