Có thể đây là câu hỏi như vậy, nhưng tôi không tìm thấy nó.Tự đăng ký cuộc gọi phương thức PropertyChanged hoặc addition trong setter?
Tôi có ứng dụng MVVM và trong ViewModel
Tôi phải thực hiện một số hành động bổ sung đối với các thay đổi của một số thuộc tính (ví dụ: nếu View
thay đổi chúng). Cách tiếp cận nào tốt hơn trong tâm trí bạn và tại sao?
1st - Thêm AdditionalAction
cuộc gọi đến setter
public class ViewModel: INotifyPropertyChanged
{
private int _MyProperty;
public int MyProperty
{
get { return _MyProperty; }
set
{
if (_MyProperty == value) return;
_MyProperty = value;
RaisePropertyChanged(() => MyProperty);
// --- ADDITIONAL CODE ---
AdditionalAction();
}
}
}
2 - Tự đăng ký INotifyPropertyChanged
public class ViewModel: INotifyPropertyChanged
{
public ViewModel()
{
// --- ADDITIONAL CODE ---
PropertyChanged += OnPropertyChanged;
}
private int _MyProperty;
public int MyProperty
{
get { return _MyProperty; }
set
{
if (_MyProperty == value) return;
_MyProperty = value;
RaisePropertyChanged(() => MyProperty);
}
}
void PropertyChanged(object sender, PropertyChangedEventArgs e)
{
// --- ADDITIONAL CODE ---
if (e.PropertyName == "MyProperty")
AdditionalAction();
}
}
Hãy tưởng tượng, mà tôi không có vấn đề hiệu suất hoặc 10'000 đối tượng. Nó chỉ là View và ViewModel. Điều gì là tốt hơn? Mã đầu tiên là "nhỏ hơn" và có ít chi phí hơn, nhưng thứ hai (trong tâm trí của tôi) rõ ràng hơn và tôi có thể sử dụng đoạn mã cho mã thuộc tính tạo tự động. Thậm chí nhiều hơn - trong trường hợp thứ 2 tôi có thể viết một cái gì đó trong xử lý sự kiện như:
On.PropertyChanged(e, p => p.MyProperty, AdditionalAction);
nơi On
là đẳng cấp helper.
Vì vậy, điều gì là tốt hơn trong tâm trí của bạn và tại sao?
CẬP NHẬT:
OK, có vẻ như tôi thấy chưa một cách tiếp cận:
3 - thêm "điểm mở rộng" trong RaisePropertyChanged:
public class NotificationObject : INotifyPropertyChanged
{
void RaisePropertyChanged(Expression<...> property)
{
// ... Raise PropertyChanged event
if (PropertyChanged != null)
// blah-blah
// Call extension point
OnPropertyChanged(property.Name);
}
public virtual OnPropertyChanged(string propertyName)
{
}
}
public class ViewModel: NotificationObject
{
private int _MyProperty;
public int MyProperty
{
get { return _MyProperty; }
set
{
if (_MyProperty == value) return;
_MyProperty = value;
RaisePropertyChanged(() => MyProperty);
}
}
override OnPropertyChanged(string propertyName)
{
if (propertyName == "MyProperty")
AdditionalAction();
}
}
Bằng cách này chúng tôi không sử dụng sự kiện, nhưng tất cả "hành động bổ sung" được gọi từ cùng một "điểm mở rộng". "Một nơi cho tất cả các hành động bổ sung" có tốt hơn "quy trình làm việc không minh bạch" không?
http://tergiver.wordpress.com/2011/01/20/self-subscription-is-asinine/ – Tergiver
sidenote: xem xét sử dụng một phương pháp helper để đưa ba dòng trong setter của tài sản của bạn một, trả về một boolean nếu thuộc tính đã thay đổi. Ngắn hơn và không trùng lặp. ví dụ 'if (RaisePropertyChanged (ref _MyProperty, value, o => o.MyProperty)) AdditionalAction();' – stijn
@Tergiver sự khác biệt giữa con đường của bạn và con đường thứ 2 của tôi là gì? Chúng giống nhau - bạn viết mã bổ sung không có trong "setter" nhưng trong "event handler" - phương thức 'OnXXX' từ quan điểm này giống như tự đăng ký sự kiện. Vì vậy, từ quan điểm của bạn, câu hỏi của tôi là - "Tốt hơn là gọi' AdditionalAction' từ setter hoặc từ phương thức OnPropertyChanged? " (ngay cả khi không có phương pháp OnPropertyChanged thực sự) – chopikadze