2015-11-10 33 views
0

我有一个包含价格和超过1000行 一个专栏中,我想减少适用于所有那些价格例如“-20%”快速地遍历datagridview的行

product price 
product1 200 
product2 300 
product3 400 

一个DataGridView
public class product 
{ 
    public int ID {get;set;} 
    public double Price {get;set;} 
    public string Name {get;set;} 
} 
public List<product> GetListProduct() 
{ 
     B_Entities dbCtx = new B_Entities(); 

     return dbCtx.B_PRODUCTS.Select(p => new Product{ ID= p.ID, Name= p.Name, Price= p.Price }).ToList(); 


} 

dgvListeProd.DataSource = GetListProduct(); 

Parallel.For(0, dgvListeProd.Rows.Count, index=> 
      { 
        object priceValue = dgvListeProd.Rows[index].Cells[2].Value; 

       if (priceValue != null) 
       { 
        decimal price = Convert.ToDecimal(priceValue); 
        decimal countedPrice = (price * pourcentage)/100; 
        countedPrice = price - countedPrice; 

        dgvListeProd.Rows[index].Cells[2].Value =(double) countedPrice; 

       } 
      }); 

这会生成一个聚合异常。 如何以快速方式执行此任务

+1

这不是一个循环,但更新的问题。你在使用数据绑定模式吗?如果是,那么数据源的类型是什么? –

+0

循环是问题,因为当我试图与普通的循环我的工作,但需要太多的时间,然后我想并行化的过程,但没有找到办法做到这一点 – MediSoft

+0

不,不是。如果你只是循环不带'dgvListeProd.Rows [index] .Cells [2] .Value =(double)countedPrice'行,你应该没有任何问题 - 现在的CPU没有1000条记录。请回答有关数据绑定或未绑定模式的问题。 –

回答

1

有一点要永久记住(或者至少对于Windows窗体:-)) - UI是单线程的,不能使用多线程技术“优化”它,包括并行扩展。

执行更新任务的最快方法是更新数据,并让UI显示您所做的事情。幸运的是,您有一个数据源,因此在数据源上应用操作(在这里您可以使用简单的forParallel.For),然后只需拨打DataGridView.Refresh即可。

这类似于你的情况下,处理1M行W/O任何问题,一个完整的工作示例:

using System; 
using System.Collections.Generic; 
using System.Linq; 
using System.Threading.Tasks; 
using System.Windows.Forms; 

namespace Samples 
{ 
    static class Program 
    { 
     static void ReducePrice(DataGridView productView, decimal percentage) 
     { 
      var factor = 1 - percentage/100; 
      var data = (List<Product>)productView.DataSource; 
      Parallel.For(0, data.Count, index => 
      { 
       var product = data[index]; 
       product.Price = (double)((decimal)product.Price * factor); 
      }); 
      productView.Refresh(); 
     } 
     [STAThread] 
     static void Main() 
     { 
      Application.EnableVisualStyles(); 
      Application.SetCompatibleTextRenderingDefault(false); 
      var form = new Form(); 
      var dg = new DataGridView { Dock = DockStyle.Fill, Parent = form }; 
      dg.DataSource = GetProductList(); 
      var button = new Button { Dock = DockStyle.Bottom, Parent = form, Text = "Reduce Price by 20%" }; 
      button.Click += (sender, e) => ReducePrice(dg, 20); 
      Application.Run(form); 
     } 
     static List<Product> GetProductList() 
     { 
      var random = new Random(); 
      return Enumerable.Range(1, 1000000).Select(n => new Product { ID = n, Name = "Product#" + n, Price = random.Next(10, 1000) }).ToList(); 
     } 
    } 
    public class Product 
    { 
     public int ID { get; set; } 
     public string Name { get; set; } 
     public double Price { get; set; } 
    } 
} 
+0

谢谢太多,它解决了问题 – MediSoft

+0

而for和Parallel.For同时,所以我应该使用简单的循环 – MediSoft

+0

@MediSoft那么,甜的是,现在你有一个选择。所以,选择你喜欢的任何东西:-) –