需求: 在一个未排序的列表中,确定是否存在重复项。
我通常会使用n平方的嵌套循环来解决这个问题。我想知道其他人是如何解决这个问题的。在Linq中是否有一种优雅、高性能的方法?最好是可以接受lambda或比较器的通用方法。
注意: 这与LINQ查找列表中的重复项不同,后者返回实际的重复项。我只需要知道是否存在重复项。
需求: 在一个未排序的列表中,确定是否存在重复项。
我通常会使用n平方的嵌套循环来解决这个问题。我想知道其他人是如何解决这个问题的。在Linq中是否有一种优雅、高性能的方法?最好是可以接受lambda或比较器的通用方法。
注意: 这与LINQ查找列表中的重复项不同,后者返回实际的重复项。我只需要知道是否存在重复项。
除非我漏掉了什么,否则您应该可以通过使用Distinct()
来简单地解决问题。尽管它可能不是您能想到的最复杂的实现,但它将告诉您是否删除了任何重复项:
var list = new List<string>();
// Fill the list
if(list.Count != list.Distinct().Count())
{
// Duplicates exist
}
.Count
和.Count()
,我需要使用.Count()
。如果不这样做,那么我会得到一个错误,指出“运算符'!='不能应用于类型为'method group'和'method group'的操作数”。 - Vincent Saelzlerint[] listOfItems = new[] { 4, 2, 3, 1, 6, 4, 3 };
var duplicates = listOfItems
.GroupBy(i => i)
.Where(g => g.Count() > 1)
.Select(g => g.Key);
foreach (var d in duplicates)
Console.WriteLine(d); // 4,3
HashSet<T>
并检查其.Add
方法的返回值。.Any
,您可以在找到重复项时立即短路枚举。public static bool ContainsDuplicates<T>(this IEnumerable<T> enumerable)
{
var knownKeys = new HashSet<T>();
return enumerable.Any(item => !knownKeys.Add(item));
}
<Extension>
Public Function ContainsDuplicates(Of T)(ByVal enumerable As IEnumerable(Of T)) As Boolean
Dim knownKeys As New HashSet(Of T)
Return enumerable.Any(Function(item) Not knownKeys.Add(item))
End Function
注意: 要检查是否没有重复项,只需将Any
更改为All
将所有项放入一个集合中,如果集合的数量与列表的数量不同,则存在重复项。
bool hasDuplicates<T>(List<T> myList) {
var hs = new HashSet<T>();
for (var i = 0; i < myList.Count; ++i) {
if (!hs.Add(myList[i])) return true;
}
return false;
}
由于无需遍历整个列表,因此应该比Distinct更高效。
foreach
。并将参数更改为IEnumerable<T>
而不是List<T>
。 - Jim Mischelvar list = new List<string> {"1", "2","3", "1", "2"};
var hasDuplicates = list.GroupBy(x => x).Any(x => x.Skip(1).Any());
类似这样的操作相对简单,能为您提供重复项的计数。
var something = new List<string>() { "One", "One", "Two", "Three" };
var dictionary = new Dictionary<string, int>();
something.ForEach(s =>
{
if (dictionary.ContainsKey(s))
{
dictionary[s]++;
}
else
{
dictionary[s] = 1;
}
});
Enumerable.Any
与 HashSet.Add
配合使用,例如:List<string> list = new List<string> {"A", "A", "B", "C", "D"};
HashSet<string> hashSet = new HashSet<string>();
if(list.Any(r => !hashSet.Add(r)))
{
//duplicate exists.
}
如果你使用整数或者有序集合,可以使用二叉树来获得O(nlog n)的性能。
或者,找到另一种更快的排序方式,然后简单地检查每个值是否与前一个值不同。
Distinct()
语句来查找唯一的记录。然后像这样与原始的泛型列表进行比较: if (dgCoil.ItemsSource.Cast<BLL.Coil>().ToList().Count != dgCoil.ItemsSource.Cast<BLL.Coil>().Select(c => c.CoilNo).Distinct().Count())
{
//Duplicate detected !!
return;
}