2013-01-08 25 views
7

Tôi thường nhận được một số cảnh báo chia sẻ lại về "các đối tượng chưa được gán được tạo bằng biểu thức 'mới'. Đoạn mã sau bị cắt phải thể hiện tình huống:Thiết kế-Mẫu để ngăn các đối tượng chưa được gán

Tôi đang sử dụng lớp trợ giúp (Observer.cs) theo dõi một số thuộc tính từ một lớp khác (MonitoredClass.cs). Khi một thuộc tính thay đổi, lớp quan sát ghi giá trị đã thay đổi vào một lớp dữ liệu khác (DataClass.cs).

đang đơn giản hóa snipped:

MonitoredClass.cs:

public class MonitoredClass : INotifyPropertyChanged 
{ 
    // simplified: in fact property calls OnPropertyChange(..) 
    public string Property1 { get; set; } 
} 

DataClass.cs:

public class DataClass 
{ 
    public string LastProperty1Value { get; set; } 
} 

Observer.cs:

public class Observer 
{ 
    private MonitoredClass _monitoredClass; 
    private DataClass _dataClass; 
    public Observer(MonitoredClass monitoredClass, DataClass dataClass) 
    { 
     _monitoredClass = monitoredClass; 
     _dataClass = dataClass; 
     _monitoredClass.PropertyChanged+=MonitoredClassPropertyChanged; 
    } 

    private void MonitoredClassPropertyChanged(..) 
    { 
     _dataClass.LastProperty1Value = _monitoredClass.Property1; 
    } 
} 

Cho đến nay rất tốt.

Nếu tôi sử dụng tại lớp Observer của tôi từ trên cao như sau:

... 
new Observer(monitoredClassInstance, dataClassInstance); 
... 

hơn tôi nhận được một cảnh báo resharper "đối tượng được gán có thể được tạo ra bởi 'mới' khái niệm".

Câu hỏi của tôi bây giờ là, nếu có giải pháp/mẫu tốt hơn để thiết kế người quan sát này. Trong số thô, tôi có thể cấp phát cá thể người quan sát mới cho trường riêng tư. Nhưng hơn tôi có một lĩnh vực mà không bao giờ được sử dụng. Hoặc tôi có thể thiết lập các surveClassInstance và dataClassInstance với các thuộc tính thay vì vượt qua chúng trong constructor. Nhưng điều này chỉ ngăn chặn cảnh báo, nhưng trên thực tế không thay đổi kiến ​​trúc.

Cảm ơn trước lời khuyên của bạn, ý kiến, mô hình, vv

+0

Bạn có chỉ định "Máy quan sát mới (mci, dci)" cho một biến không? –

+0

Điều gì ngăn cản bộ thu gom rác thu thập "Observer" mới của bạn? – Jodrell

+0

var a = Observer mới (monitoringClassInstance, dataClassInstance); – phnkha

Trả lời

8

Nó có thể là tốt như nó được. Tất nhiên, nó chỉ hoạt động bởi vì bạn đã gắn một trình xử lý sự kiện, do đó liên kết toàn bộ thời gian của Observer với phần tử MonitoredClass. Nếu bạn không kèm theo một trình xử lý sự kiện, thì người quan sát sẽ không có tham chiếu đến nó và nó sẽ (cuối cùng) là rác được thu thập.

Suy nghĩ về nó, nó có thể do đó được rõ ràng hơn để làm cho các nhà xây dựng tư nhân và viết một phương thức tĩnh nào để tạo ra nó:

public class Observer 
{ 
    private MonitoredClass _monitoredClass; 
    private DataClass _dataClass; 

    public static void Observe(MonitoredClass monitoredClass, DataClass dataClass) 
    { 
     new Observer(monitoredClass, dataClass); 
    } 

    private Observer(MonitoredClass monitoredClass, DataClass dataClass) 
    { 
     _monitoredClass = monitoredClass; 
     _dataClass = dataClass; 
     _monitoredClass.PropertyChanged+=MonitoredClassPropertyChanged; 
    } 

    private void MonitoredClassPropertyChanged(..) 
    { 
     _dataClass.LastProperty1Value = _monitoredClass.Property1; 
    } 
} 

Sau đó, bạn có thể ngăn chặn các cảnh báo bên trong Quan sát() và những người gọi nó sẽ không cần phải lo lắng về nó.

+0

bạn nói đúng. Từ bên ngoài lớp, giải pháp này trông đẹp hơn nhiều. – rhe1980

2
public class Observer 
{ 
private MonitoredClass _monitoredClass; 
private DataClass _dataClass; 

public void Setup(MonitoredClass monitoredClass, DataClass dataClass) 
{ 
    _monitoredClass = monitoredClass; 
    _dataClass = dataClass; 
    _monitoredClass.PropertyChanged+=MonitoredClassPropertyChanged; 
} 

private void MonitoredClassPropertyChanged(..) 
{ 
    _dataClass.LastProperty1Value = _monitoredClass.Property1; 
} 
} 

Observer o = new Observer(); 
o.Setup(foo, bar); 

Điều này sẽ không chỉ ngăn chặn sự cảnh báo mà còn cung cấp cho bạn một sự thay đổi để thực hiện các phương pháp khác trên người quan sát, chẳng hạn như

public void Close() 
{ 
    _monitoredClass.PropertyChanged-=MonitoredClassPropertyChanged; 
} 

nếu bạn muốn kiểm soát hủy đăng ký n cách rõ ràng.

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