我在比较C#(XNA)中的两个StringBuilder时遇到了一个小问题。
StringBuilder sb1;
StringBuilder sb2;
两者都在我的代码的不同部分初始化。一个简单的Console.WriteLine显示它们包含相同的文本。但是,以下是错误的:
sb1.Equals(sb2); // This is false
然而以下是真的
sb1.ToString().Equals(sb2.ToString); // This is true
怎么会发生这种情况?
答案 0 :(得分:7)
由于string
类会覆盖Equals
方法,因此字符串会按值而不是引用进行比较。
请参阅documentation:
尽管string是引用类型,但是定义了相等运算符(==和!=)来比较字符串对象的值,而不是引用。
它讨论了==
和!=
运算符,但实际上它们正在调用string.Equals
并且它按值比较字符串。
答案 1 :(得分:3)
Equals
上有两个StringBuilder
重载,可以做一些意想不到的事情。
Equals(Object)
重载继承自Object并比较引用。
Equals(StringBuilder)
重载比较内容,容量和MaxCapacity 。
你似乎在调用这两个重载中的第二个。
由于StringBuilder将动态扩展其容量,因此比较两个StringBuilder实例的结果取决于对每个实例执行的操作的确切顺序(例如,追加,替换,删除等)。
例如,这会给出您描述的结果:
StringBuilder sb1 = new StringBuilder(), sb2 = new StringBuilder();
sb1.Append("something").Append('1', 100).Replace("1", "");
sb2.Append("something");
Console.WriteLine(sb1.Equals(sb2)); // False
Console.WriteLine(sb1.ToString().Equals(sb2.ToString())); // True
似乎没有内置方式来比较内容,但如果您不想在比较时分配字符串,则可以轻松编写自己的比较:
public static bool Equals(StrinBuilder left, StringBuilder right)
{
if (left.Length != right.Length)
return false;
int length = left.Length;
for(int i = 0; i < length; i++)
if (left[i] != right[i])
return false;
return true;
}