以优雅而快速的方式处理列表中的重复项

本文关键字:列表 处理 方式 | 更新日期: 2023-09-27 18:22:23

dI有以下代码来检查是否存在重复的文件名,并删除具有重复文件名的文件。

我可以通过查找第一个列表中的第一个和最后一个索引,然后检查它是否不相同来做到这一点。列表项包含一个具有名称和ID的对象。列表中大约有550k个对象。

第二个循环有filesPaths列表,其中包含大约5k个文件路径。如果有一个重复的文件,并且它在第二个列表中,那么我可以删除。

以下操作需要一天多的时间才能完成。有什么办法可以缩短时间吗?

foreach (DocNameObject someObjectDataFileRow in someObjectDataFileList)
{   
  int index1 = Array.FindIndex(someObjectDataFileList.ToArray(), row => row.docName.StartsWith(someObjectDataFileRow.docName));
  int index2 = Array.FindLastIndex(someObjectDataFileList.ToArray(), row => row.docName.StartsWith(someObjectDataFileRow.docName));
  Console.WriteLine(++i);
  if (index1 != index2) 
  {
    foreach (String fileName in filesPaths)
       {
         try
         {
            if (fileName.Contains(someObjectDataFileRow.docName))
            {
               if (File.Exists(fileName))
                 File.Delete(fileName);
            }
         }catch (Exception e)
         {
            Console.WriteLine("Problem deleting:" + e.Message);
         }
       }
    }
}

以优雅而快速的方式处理列表中的重复项

您可以做的第一件事是根据docName对"someObjectDataFileList"进行排序。它可能会使index1和index2的计算变得多余。

另一个优化是在物理删除fileName后,也将其从"filePaths"列表中删除。

经过快速思考,您可以使用for(...)循环而不是foreach(..),因此您将始终拥有index1,而无需额外计算,然后,您就可以使用:

public int FindIndex(int startIndex, Predicate<T> match)

因此,您将在列表的右侧部分查找重复项,因为索引的左侧部分已经被选中。

另一件事是.ToArray()转换。您可以只转换一次枚举,而不是在每个循环中转换。