说明:
我有一个 C# 列表
List<int> numbers = new List<int> { 1, 2, 3, 2, 4, 3, 5 };
删除重复值后,列表应如下所示:
{ 1, 2, 3, 4, 5 }
使用 HashSet 是正确的方法还是有其他方法来保留列表的顺序?提供指导或示例代码。
我首先使用HashSet去除重复值,但是发现这个方法改变了元素的顺序。然后我尝试使用 for 循环和临时列表来跟踪唯一值,但这种方法似乎有点复杂且效率低下。
我希望使用一种更简单、更高效的方法来删除重复值,同时保留列表中元素的原始顺序。
您可以使用
HashSet<T>
来执行类似的操作。
IEnumerable<T> OrderedDistinct<T>(IEnumerable<T> source)
{
var set = new HashSet<T>();
foreach (var item in source)
{
if (set.Add(item))
{
yield return item;
}
}
}
有趣的是,这正是Enumerable.Distict
所做的,这意味着
Distinct
将保留源中项目的顺序。但是,文档指出“结果序列是无序的”,这意味着他们将来可以自由地更改此行为。
Distinct
上使用
List<T>
。
numbers.Distinct();
但请注意,它不能保证保留顺序 - 尽管从当前的实现来看似乎是这样。他们将来改变实施的可能性是——尽管非常低。
如果您需要这种保证,循环您的列表并记住这些项目对我来说似乎很好:
var result = new List<T>();
var uniques = new HashSet<T>();
foreach(var e in myList)
if(uniques.Add(e)
{
result.Add(e);
}
请注意,我使用 HashSet
仅用于检查 元素是否已在结果集中,而不依赖于其顺序。