2013-03-01 36 views
6

Nó không phải là quan trọng nhưng tôi đang cố gắng để tìm ra những gì nó nói với tôi và nó là một cảnh báo hợp pháp? Ai đó có thể giải thích lỗi này trong điều kiện đơn giản cho tôi?CA1001 Visual Studio 2012 Cảnh báo phân tích mã. Nó có nghĩa là gì?

CA1001 loại sở hữu ruộng dùng một lần nên dùng một lần

Thực hiện IDisposable vào 'MemVoteManager' vì nó tạo ra các thành viên của loại IDisposable sau: 'CongressDBEntities'. Nếu trước đây, 'MemVoteManager' đã được chuyển, việc thêm thành viên mới triển khai IDisposable vào loại này được coi là thay đổi đột phá đối với người tiêu dùng hiện tại .

public class MemVoteManager : AbstractDataManager, IMemVoteManager 
{ 
    private CongressDBEntities context = new CongressDBEntities(); 

    public int AddMemVote(tMemVoteScore mvs) 
    { 
     //Insert Model 
     context.tMemVoteScores.Add(mvs); 
     context.SaveChanges(); 

     int newPK = mvs.MemVoteScoresID; 

     //Update funky column ID with PK as well 
     var memVoteItem = (from m in context.tMemVoteScores 
          where m.MemVoteScoresID == newPK 
          select m).SingleOrDefault(); 

     memVoteItem.ID = memVoteItem.MemVoteScoresID; 
     context.SaveChanges(); 
     return newPK; 
    } 
+3

Sẽ rất khó để giải thích những gì cảnh báo đó cho bạn biết mà không cần lặp lại cảnh báo. Vì loại của bạn có một trường, trong đó nó xây dựng một đối tượng và lưu trữ vào nó, nơi đối tượng đó triển khai IDisposable, bạn nên triển khai IDisposable trên kiểu của bạn, xử lý đối tượng trong trường đó. Đó là cơ bản những gì cảnh báo nói. Phần thay đổi đột phá là bất kỳ mã hiện có nào sử dụng loại của bạn sẽ không được xây dựng với 'Vứt bỏ' trong tâm trí, và do đó thay đổi đột ngột của nó. –

Trả lời

7

Bạn thể thực hiện IDisposable nên bối cảnh sẽ được xử lý khi người tiêu dùng được thực hiện với lớp học của bạn, nhưng bạn có thể tốt hơn KHÔNG có ngữ cảnh là một thành viên của lớp. Chỉ cần tạo ra nó khi bạn cần đến nó và vứt bỏ nó khi bạn đã hoàn tất:

public int AddMemVote(tMemVoteScore mvs) 
{ 
    //Insert Model 
    using(CongressDBEntities context = new CongressDBEntities()) 
    { 
     context.tMemVoteScores.Add(mvs); 
     context.SaveChanges(); 

     int newPK = mvs.MemVoteScoresID; 

     //Update funky column ID with PK as well 
     var memVoteItem = (from m in context.tMemVoteScores 
          where m.MemVoteScoresID == newPK 
          select m).SingleOrDefault(); 

     memVoteItem.ID = memVoteItem.MemVoteScoresID; 
     context.SaveChanges(); 
    } 
    return newPK; 
} 

bối cảnh có trọng lượng nhẹ do đó không phải là một hình phạt rất lớn để tạo ra chúng mỗi lần. Thêm vào đó bạn không phải lo lắng về việc người tiêu dùng thông báo cho bạn về việc vứt bỏ bối cảnh, và bạn không có nhiều thay đổi trong bộ nhớ nếu một cá thể của lớp được sử dụng nhiều lần.

+0

Nhưng tôi nghĩ tất cả mọi thứ cuối cùng đã được thu gom rác sau khi nó đi ra khỏi phạm vi?Nhưng bị bệnh đi trước và quấn nó như bạn đã làm ở trên nếu điều đó sẽ làm cho phân tích mã hạnh phúc – punkouter

+1

@punkouter, vấn đề với quá trình suy nghĩ đó là có một số cách thức đối tượng *** không bao giờ *** đến thu gom rác thải. Quản lý bộ nhớ, mặc dù nó được tự động hóa trong .NET, không phải là vô nghĩa. Hãy xem xét một lớp có tham chiếu đến một lớp khác cũng được tham chiếu bởi một đối tượng tồn tại mãi mãi. Tôi biết nó có vẻ giống như một trường hợp cạnh - nhưng nó không phải. *** Không có vật thể nào trong số đó sẽ bị thu gom rác cho đến khi ứng dụng tắt. –

+0

Ok. Vì vậy, thực hiện I dùng một lần và gọi nó là một cách để đảm bảo rằng các lớp sẽ được thu thập rác ... Có lẽ nó không cần thiết bây giờ nhưng nó là thực hành tốt nhất để luôn luôn thực hiện nó anyways chỉ trong – punkouter

3

Nó cho bạn biết rằng lĩnh vực context chứa các thành viên dùng một lần. Điều đó có nghĩa là các thành viên đó cần phải có Dispose() gọi chúng để Bộ sưu tập rác có thể xảy ra. Do đó, nó muốn bạn triển khai giao diện IDisposable trên MemVoteManager để bạn có thể gọi Dispose() về ngữ cảnh và/hoặc các thành viên sử dụng một lần.

Vì vậy, sửa đổi bạn mã như vậy:

public class MemVoteManager : AbstractDataManager, IMemVoteManager, IDisposable 

và sau đó thực hiện các thành viên của giao diện IDisposable như thế này:

public void Dispose() 
{ 
    // call dispose on the context and any of its members here 
} 
+0

Vì vậy, bất kỳ lớp bên trong lớp học của tôi mà thực hiện Idisposable có nghĩa là tôi cần phải thực hiện iDisposable là tốt? Nếu không có nó tôi có thể tạo ra một rò rỉ bộ nhớ? Giống như tôi đã đề cập ở trên, mặc dù tất cả mọi thứ là rác thu thập được .. mã được quản lý của nó! – punkouter

+0

@punkouter, nếu lớp thực hiện 'IDisposable' có nghĩa là nó có tài nguyên không được quản lý để loại bỏ. Một kết nối cơ sở dữ liệu cho ví dụ *** (kết nối thực tế) *** - đó là một tài nguyên không được quản lý. Vì vậy, vì bạn có một đối tượng bối cảnh, trong đó có các đối tượng khác mà cuối cùng dẫn đến các tài nguyên không được quản lý, bạn cần ** đảm bảo ** rằng bạn nhận được 'Dispose()' được gọi trên chúng. –

+0

nhưng gói DBcontext với một 'sử dụng' sẽ giống như thực hiện một idisposable? – punkouter

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