C# == 运算符详细做了什么?

2022-09-03 09:16:05

在c#中,当您在两个对象上与“==”运算符进行比较时,后台究竟发生了什么?它只是比较地址吗?还是像 Equals() 或 CompareTo() ?

PS:Java中的“==”运算符呢?它的行为是一样的吗?


答案 1

据我所知:

  • 它按值比较值类型(相等)
  • 它按引用(标识)比较引用类型
  • 除非 == 运算符重载,否则它将调用该运算符。

Equals 在 object 中实现,也可以被覆盖。Object 中的默认实现对引用类型执行引用比较。因此,默认情况下,Equals 和 == 执行相同的操作。

我认为在java中你不能重载==运算符。但是我的Java知识已经过时了。

编辑:请注意,该运算符是一个静态方法。它是在编译时绑定的,基于变量或字段的类型。 是在运行时基于实际运行时类型找到的虚拟方法。==Equals


答案 2

作为 Stefan 优秀答案的扩展 - 另一个例外是如果操作数涉及 - 在这种情况下,“提升”运算符适用(ECMA 334v4 中的 14.2.7):Nullable<T>

对于相等运算符 == !=

如果操作数类型都是不可为空的值类型,并且结果类型是 bool,则存在运算符的提升形式。提升的形式是通过添加单个 ?每个操作数类型的修饰符。提升的运算符将两个 null 值视为相等,并且 null 值不等于任何非 null 值。如果两个操作数都非空,则提升的运算符将解开操作数的包装,并应用基础运算符以生成布尔结果。

这意味着:因为(比如说)之间有一个相等运算符:

int i = ..., j = ...;
bool eq = i == j;

因此,存在一个形式的隐式运算符(尽管操作方式不同):

int? i = ..., j = ...;
bool eq;
if(i.HasValue) {
    if(j.HasValue) { // both have values; compare
       eq = i.GetValueOrDefault() == j.GetValueOrDefault();
    } else { // one null; always false
       eq = false;
    }
} else { // true if both null, else false
    eq = !j.HasValue;
}