StringComparer.InvariantCultureIgnoreCase Equals vs GetHashCode不赞成相等的对象 [英] StringComparer.InvariantCultureIgnoreCase Equals vs GetHashCode disagree for equal objects

查看:83
本文介绍了StringComparer.InvariantCultureIgnoreCase Equals vs GetHashCode不赞成相等的对象的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

StringComparer.InvariantCultureIgnoreCase Equals对于 vs \0返回true,但是GetHashCode返回两个字符串的不同值。

StringComparer.InvariantCultureIgnoreCase Equals returns true for "" vs "\0", but GetHashCode return different values for the two strings. Is this a bug?

var sc = StringComparer.InvariantCultureIgnoreCase;
string s1 = "";
string s2 = "\0";
Console.WriteLine( sc.Equals(s1, s2)  );
Console.WriteLine( sc.GetHashCode(s1) );
Console.WriteLine( sc.GetHashCode(s2) );

返回

True
0
-1644535362

我认为GetHashCode应该对于相等的字符串返回相同的值,这是一个错误吗?

I thought that GetHashCode should return the same value for 'equal' strings, so is this a bug?

推荐答案

这2个字符串不是按位相等的。它们是2种不同的长度。因此,哈希码算法在这里是合理的。

Those 2 strings are not bitwise equals. They are 2 different lengths. Hence, the hash code algorithm is being reasonable here.

字符串比较算法在进行比较时必须忽略 \0 。我查看了源代码:它正在执行某种加/减比较算法,以找出是否有所不同。

The string comparison algorithm must be ignoring \0 when doing its comparisons. I looked into the source: It is doing some sort of add/subtract comparison algorithm to find out if things are different.

GetHashCode 仅表示值可以相等,不一定相同。相反的情况并不总是正确的,您可以覆盖 == 运算符或 .Equals 并将其产生 true ,当哈希码不一致时。

GetHashCode only implies that values may be equal, not necessarily they are. The inverse is not always true, you can override the == operator or .Equals for any type and have it produce true when the hash codes don't agree.

此处为 GetHashCode 。似乎是在使用原始字节进行计算。

Here's GetHashCode. It looks like it's using the raw bytes for calculation.

您可能偶然发现了.NET库中一个不起眼的错误,但我猜测这是一个优势

You may have stumbled on an obscure bug in the .NET libraries, but I'm guessing that this is an edge case.

然后再次-您正在使用字符串比较器。不是 string.Equals 方法或 string.GetHashCode 。请注意, Console.WriteLine( \0 .Equals()); 产生 false

Then again - you are using a string comparer. Not the string.Equals method or string.GetHashCode. Notice that Console.WriteLine("\0".Equals("")); produces false.

如果您希望一个字符串比较器同意它,我相信 StringComparer.OrdinalIgnoreCase 可以解决问题因为它分别查看每个字符,而不是对值进行排序。 看起来它们都只是漏到了相同的字符比较方法。

If you want a string comparer that would have it agree, I believe StringComparer.OrdinalIgnoreCase would do the trick since it looks at each character separately, instead of collating on the values. It looks like both just funnel to the same character comparison method.

这篇关于StringComparer.InvariantCultureIgnoreCase Equals vs GetHashCode不赞成相等的对象的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆