gpt4 book ai didi

c# - 实现 IEqualityComparer

转载 作者:太空狗 更新时间:2023-10-29 18:11:58 25 4
gpt4 key购买 nike

我想从列表中获取不同的对象。我尝试实现 IEqualityComparer 但没有成功。请查看我的代码并给我一个关于 IEqualityComparer 的解释。

public class Message
{
public int x { get; set; }
public string y { get; set; }
public string z { get; set; }
public string w { get; set; }
}

public class MessageComparer : IEqualityComparer<Message>
{
public bool Equals(Message x, Message y)
{
if (Object.ReferenceEquals(x, y)) return true;

if (Object.ReferenceEquals(x, null) || Object.ReferenceEquals(y, null))
return false;

if (x.x == y.x && x.y == y.y && x.z == y.z && x.w == y.w)
{
return true;
}

return false;
}

public int GetHashCode(Message number)
{
// if (Object.ReferenceEquals(number, null)) return 0;
int hashX = number.x.GetHashCode();
int hashY = number.y == null ? 0 : number.y.GetHashCode();
int hashZ = number.z == null ? 0 : number.z.GetHashCode();
int hashW = number.w == null ? 0 : number.w.GetHashCode();

return hashX ^ hashY ^ hashZ ^ hashW;
}
}

这是我的 ListMessage 对象:

Message m1 = new Message();
m1.x = 1;
m1.y = "A";
m1.z = "B";
m1.w = "C";

Message m2 = new Message();
m2.x = 1;
m2.y = "A";
m2.z = "B";
m2.w = "C";

Message m3 = new Message();
m3.x = 1;
m3.y = "A";
m3.z = "B";
m3.w = "C";

Message m4 = new Message();
m4.x = 2;
m4.y = "A";
m4.z = "B";
m4.w = "C";

Message m5 = new Message();
m5.x = 3;
m5.y = "W";
m5.z = "D";
m5.w = "C";

Message m6 = new Message();
m6.x = 4;
m6.y = "S";
m6.z = "F";
m6.w = "R";

List<Message> collection = new List<Message>();
collection.Add(m1);
collection.Add(m2);
collection.Add(m3);
collection.Add(m4);
collection.Add(m5);

collection.Distinct(new MessageComparer());

当我调用Distinct()方法时,collection中的元素个数是一样的。

最佳答案

试试这个:

var distinct = collection.Distinct(new MessageComparer());

然后使用distinct之后的任何事情。

您似乎忘记了 IEnumerable<> 的不变性. LINQ 方法都没有真正改变原始变量。相反,他们返回 IEnuerable<T> s 其中包含表达式的结果。例如,让我们考虑一个简单的 List<string> original内容{ "a", "a", "b", "c" } .

现在,让我们调用original.Add("d"); .该方法没有返回值(它是 void )。但是如果我们打印出 original 的内容,我们将看到 { "a", "a", "b", "c", "d" } .

另一方面,我们现在调用original.Skip(1) .此方法确实有一个返回值,类型为 IEnumerable<string> .它是一个 LINQ 表达式,不会对原始集合执行任何副作用操作。因此,如果我们调用它并查看 original ,我们将看到 { "a", "a", "b", "c", "d" } .但是,该方法的结果将为 { "a", "b", "c", "d" } .如您所见,结果跳过了一个元素。

这是因为 LINQ 方法接受 IEnumerable<T>作为参数。因此,他们对原始列表的实现没有概念。您可以通过扩展方法传递 ReadOnlyCollection他们仍然可以通过它进行评估。然后,他们不能更改原始集合,因为可以用多种方式编写原始集合。

所有这些,但以表格形式。每行以原始 { "a", "a", "b", "c" } 开头:

Context     Example function    Immutable?    Returned Value     Collection after calling
Collection Add("d") No (void) { "a", "a", "b", "c", "d" }:
LINQ Skip(1) Yes { "a", "b", "c" } { "a", "a", "b", "c" }:

关于c# - 实现 IEqualityComparer,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/24924071/

25 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com