字符串的行为.等于和==

本文关键字:字符串 | 更新日期: 2023-09-27 18:01:31

昨天当我在这里张贴一个问题的答案时,我遇到了String.Equals==在不同情况下表现不同的问题。

我想要得出String.Equals==行为的结论。

bool result = false;
    object obj = "String"; 
    string str2 = "String";
    string str3 = typeof(string).Name;
    string str4 = "String";
    object obj2 = str3; 
    // obj, str2, str4 references are same.
    // obj is object type and others are string type
    // Comparision between object obj and string str2 -- Com 1
    result = String.Equals(obj, str2);// true
    result = String.ReferenceEquals(obj, str2); // true
    result = (obj == str2);// true
    // Comparision between object obj and string str3 -- Com 2
    result = String.Equals(obj, str3);// true
    result = String.ReferenceEquals(obj, str3); // false
    result = (obj == str3);// false
    // Comparision between object obj and string str4 -- Com 3
    result = String.Equals(obj, str4);// true
    result = String.ReferenceEquals(obj, str4); // true
    result = (obj == str4);// true
    // Comparision between string str2 and string str3 -- Com 4
    result = String.Equals(str2, str3);// true
    result = String.ReferenceEquals(str2, str3); // false
    result = (str2 == str3);// true
    // Comparision between string str2 and string str4 -- Com 5
    result = String.Equals(str2, str4);// true
    result = String.ReferenceEquals(str2, str4); // true
    result = (str2 == str4);// true
    // Comparision between string str3 and string str4 -- Com 6
    result = String.Equals(str3, str4);// true
    result = String.ReferenceEquals(str3, str4); // false
    result = (str3 == str4);// true
    // Comparision between object obj and object obj2 -- Com 7
    result = String.Equals(obj, obj2);// true
    result = String.ReferenceEquals(obj, obj2); // false
    result = (obj == obj2);// false

我看手表也

obj     "String" {1#}   object {string}
str2    "String" {1#}   string
str3    "String" {6#}   string
str4    "String" {1#}   string
obj2    "String" {6#}   object {string}

阅读这里和这里的文章

Com1, Com2, Com3, Com4, Com5和Com6为什么有不同的行为?

字符串的行为.等于和==

==操作符对于strings和所有其他引用类型具有不同的行为。如果==的两个操作数都是string,则使用String.Equals比较。否则==等于Object.ReferenceEquals

来自c# == Operator文档:

对于预定义的值类型,相等操作符(==)返回true其操作数的值相等,否则为false。供参考非string类型,如果其两个操作数引用,==返回true同样的物体。类型的值进行比较字符串。

您看到的另一个效果是字符串交互。在您的代码中只有一个对文字"String"值的引用。您的代码相当于:obj = str2 = str4 = "String"。Obj、str2和str4都是对同一个底层字符串的引用。由于str3是在运行时生成的,因此它被设置为具有相同值" string "的不同字符串。

总结:

  1. com1: result = (obj == str2);//true
    • 比较objectstring,因此执行引用相等性检查
    • obj和str2指向相同的引用,所以结果为true
  2. result = (obj == str3);//false
    • 比较objectstring,因此执行引用相等性检查
    • obj和str3指向不同的引用,所以结果是false
  3. result = (obj == str4);//true
    • 比较objectstring,因此执行引用相等性检查
    • obj和str4指向相同的引用,所以结果为true
  4. result = (str2 == str3);//true
    • 比较stringstring,因此执行字符串值检查
    • str2和str3都是"String"所以结果为真
  5. result = (str2 == str4);//true
    • 比较stringstring,因此执行字符串值检查
    • str2和str4都是"String"所以结果是true
  6. result = (str3 == str4);//true
    • 比较stringstring,因此执行字符串值检查
    • str3和str4都是"String"所以结果是true
  7. result = (obj == obj2);//false-比较objectobject,执行引用相等性检查- obj和obj2指向不同的引用,所以结果是false

请记住,==执行的比较类型是在编译时选择的,因此它基于操作数的静态类型。编译器不知道obj和obj2总是指向字符串。

Equals比较引用类型的引用和值类型的值。String是一个引用类型,其行为类似于值类型。String可以存储大量数据,这就是为什么它应该存储在堆上,但它是不可变的,并且像任何其他值类型一样。

String上的Equals方法将字符串的值与另一个对象(必须是String)的值进行比较。

ReferenceEquals判断两个引用类型是否为同一实例。由于String s是引用类型,但不可变,因此它们被internned以允许相同的字符串字面值被不同的字符串引用。

最后,相等运算符检查String s的值是否相等。对于

typeof(string).Name == (object)"String"

结果将返回false,因为左操作数实际上是嵌入在字符串类型定义中的常量,不共享对字符串文字的相同引用,并且由于右操作数被装箱,它们的引用被比较。