ObservableCollection并乘以NotifyPropertyChanged

时间:2014-01-31 09:48:59

标签: c# wpf class observablecollection inotifypropertychanged

我对ObservableCollection有一些问题。

基本上问题是,我需要改变很多属性取决于那些,改变了什么。

例如:

下面你可以看到ProductCount方法,它改变了ListView上选择的产品的数量(数量)(ListView有ObservableCollection绑定)。

因此,当我更改ProductCount时,我还需要更改DiscountPrice(当产品有折扣时),ProductPrice(即Count * Price),DiscountValue(如果项目有50%折扣,重新计算), ReceiptSum(所有ProducPrice * ProductCount的总和),以及项目被发送到厨房的背景。

public decimal ProductCount
{
    get 
    {
        //get count from database
        return _productCount;
    }
    set
    {
        _productCount = value;
        //update count in database
        NotifyPropertyChanged("ProductCount");
        NotifyPropertyChanged("DiscountPrice");
        NotifyPropertyChanged("ProductPrice");
        NotifyPropertyChanged("DiscountValue");
        NotifyPropertyChanged("TotalValue");
        NotifyPropertyChanged("ReceiptSum);
        NotifyPropertyChanged("SentToKichen");
    }
}

嗯,一切似乎都很安静,但是。问题是,这花了很多时间来改变一切。例如,在我的8核PC上,16GB RAM,改变一些值需要4秒。此时申请被冻结, 这是我想解决的问题。

也许您有任何想法如何更改我的源代码,更快地重新计算所有值?

提前致谢!

3 个答案:

答案 0 :(得分:0)

我建议你使用异步Dispatcher.BeginInvoke方法。它将在UI线程中执行异步调用,因此应用程序不应该冻结。请注意,只有在您不需要即时通知时,此解决方案才有效。 如果ProductCount在继承DependencyObject的类中,请使用Dispatcher,否则可以使用Deployment.Current.Dispatcher。

public decimal ProductCount
{
    get 
    {
        //get count from database
        return _productCount;
    }
    set
    {
        _productCount = value;
        //update count in database
        Dispatcher.BeginInvoke(new Action(() => 
        {
            NotifyPropertyChanged("ProductCount");
            NotifyPropertyChanged("DiscountPrice");
            NotifyPropertyChanged("ProductPrice");
            NotifyPropertyChanged("DiscountValue");
            NotifyPropertyChanged("TotalValue");
            NotifyPropertyChanged("ReceiptSum);
            NotifyPropertyChanged("SentToKichen");
        }
    }
}

答案 1 :(得分:0)

查看代码中的注释,我怀疑问题的最大原因是每次读取属性时,都是从数据库中获取它。这意味着如果您有 n 属性,并且您正在显示 m 记录,那么当UI到达所有属性的数据绑定时,您将创建 nxm 数据库调用,肯定无法很好地扩展。

更好的方法是在一次点击中请求数据,从结果中构建视图模型。当您需要刷新数据时(如产品计数更改的情况),然后一次点击数据库并更新各种属性 - 这反过来将导致各种属性更改事件触发。

答案 2 :(得分:0)

您可以在背景工作者中进行必须进行的每项更改,以加快治疗效果。

最好在viewModel中完成工作,更新View然后更新模型