C# 运算符 ==、StringBuilder.Equals、Object.Equals 和 Object.ReferenceEquals 之间的区别
Posted
技术标签:
【中文标题】C# 运算符 ==、StringBuilder.Equals、Object.Equals 和 Object.ReferenceEquals 之间的区别【英文标题】:C# Differences between operator ==, StringBuilder.Equals, Object.Equals and Object.ReferenceEquals 【发布时间】:2013-04-29 06:42:34 【问题描述】:我对@987654321@ 和Equals(object)
有疑问。我的示例代码如下:
class Program
static void Main(string[] args)
var sb1 = new StringBuilder("Food");
var sb2 = new StringBuilder("Food");
Console.WriteLine(sb1 == sb2);
Console.WriteLine(sb1.Equals(sb2));
Console.WriteLine(Object.Equals(sb1, sb2));
Console.WriteLine(Object.ReferenceEquals(sb1, sb2));
Console.ReadLine();
输出是:
False
True
False
False
但就我而言,Object.Equals(sb1, sb2)
内部调用 sb1.Equals(sb2)
那么为什么它会给出两个不同的结果呢?
【问题讨论】:
你应该想出一个更好的问题标题。电流没有任何意义。请不要在标题中重复标签。 @ReferenceEquals:你是比较四种比较方法。我修改了你的标题以更好地反映你的问题。 为什么要检查 2 个字符串生成器的相等性?这就像检查流或文本编写器是否相等。 【参考方案1】:你错过了另一个测试:
Console.WriteLine(sb1.Equals((object)sb2)); // False!
StringBuilder 不会覆盖Equals(object)
,它会重载另一个Equals(StringBuilder)
。
Object.Equals(object, object)
正在调用Equals(object)
,所以结果为假。
【讨论】:
重载Equals
而不覆盖它。 WTF他们认为。就我个人而言,我会使用引用相等,但这种选择只是令人困惑。
你应该解释一下Object.Equals()
和IEquatable<T>
之间的区别
因为我们有两个不同的引用(对象、实例)并且默认的 Equal(object) 应该首先返回引用比较。
@MatthewWatson - 我不认为 StringBuild 实现了 IEquatable<T>
: msdn.microsoft.com/en-us/library/system.text.stringbuilder.aspx
@Kobi 是的,虽然它确实有一些与之匹配的东西。奇怪的是他们没有添加接口。可能这将是一个突破性的变化。【参考方案2】:
您使用了 4 种不同的比较方法,导致不同的结果:
操作员==
默认情况下会检查引用是否相等。在这种情况下,您有两个实例,因此它们确实有两个不同的引用。 ==
的行为可以被任何类型覆盖(例如 string
有自己的比较方法),但在 StringBuilder
的情况下则不然。
方法StringBuilder.Equals(StringBuilder)
将与另一个StringBuilder 比较并比较一些内部值。在您的情况下,这些值是相同的。奇怪的是StringBuilder
并没有覆盖StringBuilder.Equals(object)
方法以应用相同的逻辑。
方法object.Equals(object, object)
将尝试调用其中一个对象的方法.Equals(object)
。在这种情况下:StringBuilder.Equals(object)
,正如我所说,它没有比较值的逻辑。结果只是比较了两个实例的引用。
Object.ReferenceEquals
只会比较参考文献。
有关详细信息,请参阅:
http://msdn.microsoft.com/en-us/library/f37cfeys.aspx http://msdn.microsoft.com/en-us/library/w4hkze5k.aspx http://msdn.microsoft.com/en-us/library/system.object.referenceequals.aspx【讨论】:
【参考方案3】:StringBuilder.equals 不比较对象,而是比较 来自MSDN:
"如果此实例和 sb 具有相等的 string、Capacity,则为真, 和 MaxCapacity 值;否则为假。”
你正在做的其余检查比较参考。
【讨论】:
以上是关于C# 运算符 ==、StringBuilder.Equals、Object.Equals 和 Object.ReferenceEquals 之间的区别的主要内容,如果未能解决你的问题,请参考以下文章