Bắt đầu với những lớp đơn giản này ...
Hãy nói rằng tôi có một tập hợp các lớp đơn giản như thế này:
class Bus
{
Driver busDriver = new Driver();
}
class Driver
{
Shoe[] shoes = { new Shoe(), new Shoe() };
}
class Shoe
{
Shoelace lace = new Shoelace();
}
class Shoelace
{
bool tied = false;
}
A Bus
có a Driver
, Driver
có hai Shoe
s, mỗi Shoe
có a Shoelace
. Tất cả đều rất ngớ ngẩn.
Thêm một đối tượng IDis Dùng cho Shoelace
Sau đó tôi quyết định rằng một số thao tác trên Shoelace
có thể là đa luồng, vì vậy tôi thêm một EventWaitHandle
cho các luồng để giao tiếp. Vì vậy, Shoelace
bây giờ trông như thế này:
class Shoelace
{
private AutoResetEvent waitHandle = new AutoResetEvent(false);
bool tied = false;
// ... other stuff ..
}
Triển khai IDis Dùng trên Dây giày
Nhưng bây giờ FxCop của Microsoft sẽ phàn nàn: "Triển khai IDis Dùng trên 'Dây giày' vì nó tạo ra các thành viên của các loại IDis Dùng sau: 'EventWaitHandle'."
Được rồi, tôi thực hiện IDisposable
trên Shoelace
và lớp nhỏ gọn của tôi trở nên lộn xộn khủng khiếp này:
class Shoelace : IDisposable
{
private AutoResetEvent waitHandle = new AutoResetEvent(false);
bool tied = false;
private bool disposed = false;
public void Dispose()
{
Dispose(true);
GC.SuppressFinalize(this);
}
~Shoelace()
{
Dispose(false);
}
protected virtual void Dispose(bool disposing)
{
if (!this.disposed)
{
if (disposing)
{
if (waitHandle != null)
{
waitHandle.Close();
waitHandle = null;
}
}
// No unmanaged resources to release otherwise they'd go here.
}
disposed = true;
}
}
Hoặc (như được chỉ ra bởi các nhà bình luận) vì Shoelace
bản thân nó không có tài nguyên không được quản lý, tôi có thể sử dụng triển khai xử lý đơn giản hơn mà không cần Dispose(bool)
và Destructor:
class Shoelace : IDisposable
{
private AutoResetEvent waitHandle = new AutoResetEvent(false);
bool tied = false;
public void Dispose()
{
if (waitHandle != null)
{
waitHandle.Close();
waitHandle = null;
}
GC.SuppressFinalize(this);
}
}
Xem trong kinh dị khi lây lan IDis Dùng
Đúng là đã sửa. Nhưng bây giờ FxCop sẽ phàn nàn rằng Shoe
tạo ra một Shoelace
, vì vậy Shoe
cũng phải như IDisposable
vậy.
Và Driver
tạo ra Shoe
như vậy Driver
phải được IDisposable
. Và Bus
tạo ra Driver
như vậy Bus
phải được IDisposable
và như vậy.
Đột nhiên, sự thay đổi nhỏ của tôi Shoelace
gây ra cho tôi rất nhiều công việc và ông chủ của tôi đang tự hỏi tại sao tôi cần phải kiểm tra Bus
để thực hiện một thay đổi Shoelace
.
Câu hỏi
Làm thế nào để bạn ngăn chặn sự lây lan này IDisposable
, nhưng vẫn đảm bảo rằng các đối tượng không được quản lý của bạn được xử lý đúng cách?