我有一个名为“fnc”的2D列表(嵌套列表),我想删除重复项并使用LINQ在富文本框中显示。我试过“groupby”但它没有用。我怎样才能做到这一点?谢谢你的帮助。
var grptest = fnc.GroupBy(x=>x);
foreach (var sublist in grptest)
{
foreach (var value in sublist)
{
ResultRTB.AppendText(value.ToString());
}
}
我在
中有这些值fnc = ((C1,C2,C3),(C2),(C1,C3),(C1,C3),(C1,C2,C3),(C3))
我想删除重复的结果将是
fnc = ((C1,C2,C3),(C2),(C1,C3),(C3))
答案 0 :(得分:2)
默认GroupBy()和Distinct()不会执行您想要的操作,因为您正在查找不同的列表,而不是这些列表中的单个值。由于List是引用类型,因此两个列表可能具有相同的元素,但Distinct()仍将返回两个列表。
如果你想(正如你在评论中所说):
fnc =((C1,C2,C3),(C2),(C1,C3),(C1,C3),(C1,C2,C3),(C3))我想删除重复的结果将是fnc =((C1,C2,C3),(C2),(C1,C3),(C3))
然后您可以使用Distinct,但提供您自己的Equality Comparer。这要求您重写Equals(表示两个列表中的值相同时)并实现GetHashCode()方法。 GetHashCode()的代码取自here。如果您想了解更多有关您需要Equals和GetHashCode的原因,请参阅here。
以下代码的输出为:
Fill
( 1 2 )
( 1 )
( 1 2 )
( 1 )
( 1 2 )
De-dupe
( 1 2 )
( 1 )
代码:
static class Program
{
class ListEqualityComparer : IEqualityComparer<List<int>>
{
public bool Equals( List<int> x, List<int> y )
{
return ( x.Count == y.Count ) && new HashSet<int>( x ).SetEquals( y );
}
public int GetHashCode( List<int> list )
{
int hash = 19;
foreach( int val in list )
{
hash = hash * 31 + val.GetHashCode();
}
return hash;
}
}
//Fill is just a method to fill the original lists for testing
static void Fill( List<List<int>> toFill )
{
Console.WriteLine( "Fill" );
for( int i = 1; i <= 5; i++ )
{
Console.Write( "( " );
List<int> newList = new List<int>();
toFill.Add(newList);
for( int j = 1; j <= i%2 + 1; j++ )
{
newList.Add( j );
Console.Write( j + " " );
}
Console.WriteLine( ")" );
}
}
static void Main( string[] args )
{
List<string> result = new List<string>();
List<List<int>> fnc = new List<List<int>>();
Fill( fnc );
var results = fnc.Distinct( new ListEqualityComparer() );
Console.WriteLine( "De-dupe" );
foreach( var list in results )
{
Console.Write( "( " );
foreach( var element in list )
{
Console.Write( element + " " );
}
Console.WriteLine( ")" );
}
}
}
答案 1 :(得分:1)
我将基于您的评论假设您正在使用字符串,因为您没有真正指定其他方式。列表是对象,因此它们具有引用。所以在下面的例子中,
var fnc = new List<List<string>>
{
new List<string>{"a", "b", "c"},
new List<string>{"a", "b", "c"}
};
var groupedFnc = fnc.GroupBy(x => x);
var distinctFnc = fnc.Distinct();
对GroupBy
和Distinct
的调用不会对列表执行任何操作,因为每个列表的引用确实已经是唯一的。在这种情况下你需要做的是写一个自定义函数传递给组,它会遍历列表并识别哪个内部列表是这个列表的重复。
另一个替代方法是编写自定义比较器类并覆盖Equals
和GetHashCode
实现并提供自己的实现,以便在执行GroupBy操作时,引用不是导致重复的部分不被识别。有关如何执行此操作的更多信息: