如何让我的程序运行得更快

时间:2018-03-15 01:52:57

标签: c# excel algorithm duplicates

我在c#中创建了一个读取和删除重复项的程序。它适用于0-5000个值,但是当我尝试使用100,000个值时,它需要太长时间或不响应。有关如何解决它的任何建议?下面是我的算法。

try
{
DataTable dtExcel = new DataTable();
dtExcel = ReadExcel(filePath, fileExt); //read excel file  

dataGridView1.DataSource = dtExcel;

mydatagrid.Rows.Clear();
for (int i = 1; i < dataGridView1.Rows.Count; i++)
{
    string exists = "no";

    //MessageBox.Show(dataGridView1.Rows[i].Cells[0].Value.ToString());

    if (mydatagrid.Rows.Count == 1)
    {
        mydatagrid.Rows.Add(dataGridView1.Rows[i].Cells[0].Value.ToString(), dataGridView1.Rows[i].Cells[1].Value.ToString(), dataGridView1.Rows[i].Cells[2].Value.ToString(), dataGridView1.Rows[i].Cells[3].Value.ToString());
    }
    else
    {
        int b = 1;
        while (b < (mydatagrid.Rows.Count - 1))
        {
            //MessageBox.Show(mydatagrid.Rows[b].Cells[0].Value.ToString());
            if (dataGridView1.Rows[i].Cells[0].Value.ToString() == mydatagrid.Rows[b].Cells[0].Value.ToString())
            {
                exists = "yes";
            }
            else
            {

            }
            b++;
        }

        if (exists == "no")
        {
            mydatagrid.Rows.Add(dataGridView1.Rows[i].Cells[0].Value.ToString(), dataGridView1.Rows[i].Cells[1].Value.ToString(), dataGridView1.Rows[i].Cells[2].Value.ToString(), dataGridView1.Rows[i].Cells[3].Value.ToString());

        }

    }
}   

2 个答案:

答案 0 :(得分:3)

Bools比字符串(exists)快,并且还要使用正确的类型。当您拥有所需信息时,应该停止循环(break)。如果你能找到一种方法来将你的特殊条件移动到1循环外(我认为你可以),你应该这样做。

  try
  {
    DataTable dtExcel = new DataTable();
    dtExcel = ReadExcel(filePath, fileExt); //read excel file  

    dataGridView1.DataSource = dtExcel;

    mydatagrid.Rows.Clear();
    for (int i = 1; i < dataGridView1.Rows.Count; i++)
    {
      bool exists = false;


      if (mydatagrid.Rows.Count == 1)
      {
        mydatagrid.Rows.Add(dataGridView1.Rows[i].Cells[0].Value.ToString(), dataGridView1.Rows[i].Cells[1].Value.ToString(), dataGridView1.Rows[i].Cells[2].Value.ToString(), dataGridView1.Rows[i].Cells[3].Value.ToString());
      }
      else
      {
        for (int b = 1; b < (mydatagrid.Rows.Count - 1); b++)
        {
          //MessageBox.Show(mydatagrid.Rows[b].Cells[0].Value.ToString());
          if (dataGridView1.Rows[i].Cells[0].Value.ToString() == mydatagrid.Rows[b].Cells[0].Value.ToString())
          {
            exists = true;
            break;
          }
        }

        if (!exists)
        {
          mydatagrid.Rows.Add(dataGridView1.Rows[i].Cells[0].Value.ToString(), dataGridView1.Rows[i].Cells[1].Value.ToString(), dataGridView1.Rows[i].Cells[2].Value.ToString(), dataGridView1.Rows[i].Cells[3].Value.ToString());

        }

      }
    }
  }

此外,您可以重写这样的全部内容,它会更快(关键是一个哈希集,可以跟踪您已添加的项目,或多或少立即告诉您是否给定的字符串已经或者没有添加):

  try
  {
    DataTable dtExcel = new DataTable();
    dtExcel = ReadExcel(filePath, fileExt); //read excel file  
    HashSet<string> addedItems = new HashSet<string>();
    dataGridView1.DataSource = dtExcel;

    mydatagrid.Rows.Clear();
    for (int i = 1; i < dataGridView1.Rows.Count; i++)
    {
      if (!addedItems.Contains(dataGridView1.Rows[i].Cells[0].Value.ToString()))
      {
        mydatagrid.Rows.Add(dataGridView1.Rows[i].Cells[0].Value.ToString(), dataGridView1.Rows[i].Cells[1].Value.ToString(), dataGridView1.Rows[i].Cells[2].Value.ToString(), dataGridView1.Rows[i].Cells[3].Value.ToString());
        addedItems.Add(dataGridView1.Rows[i].Cells[0].Value.ToString());
      }
    }
  }

答案 1 :(得分:2)

  1. 从字符串更改为bool
  2. 创建工作任务,每个任务的循环次数少于5000(通过工作查找),请参阅Task.wait https://msdn.microsoft.com/en-us/library/dd235635(v=vs.110).aspx
  3. 在过滤两次数据完成后使用mydatagrid.Rows.Add,首先将其存储在List上并使用linq查找数据(where)而不是。见https://docs.microsoft.com/en-us/dotnet/api/system.linq.enumerable.where?view=netframework-4.7.1
  4. 我认为它可以帮到你一点......