使用变体泛型委托类型对运算符 == 进行重载解析

2024-04-28

重载解析的精确规则是什么==两个委托类型表达式之间?

考虑以下代码(其中using System;是需要的):

static class ProgramA
{
    static void TargetMethod(object obj)
    {
    }

    static void Main()
    {
        Action<object> instance1 = TargetMethod;
        Action<object> instance2 = TargetMethod;

        Action<string> a1 = instance1;
        Action<Uri> a2 = instance2;

        Console.WriteLine((object)a1 == (object)a2);
        Console.WriteLine((Delegate)a1 == (Delegate)a2);
        Console.WriteLine((Action<object>)a1 == (Action<object>)a2);

        Console.WriteLine(a1 == a2);  // warning CS0253: Possible unintended reference comparison; to get a value comparison, cast the right hand side to type 'System.Action<string>'
    }
}

解释:

instance1 and instance2是同一运行时类型的两个单独实例,通用Action<in T>这是逆变 in T。这些实例是不同的,但是Equals因为他们有相同的目标。

a1 and a2instance1 and instance2,但由于逆变Action<in T>存在implicit参考转换自Action<object>给每一个Action<string> and Action<System.Uri>.

现在,C# 语言规范(以及其他重载)具有这些operator ==:

bool operator ==(object x, object y);                   // §7.10.6
bool operator ==(System.Delegate x, System.Delegate y); // §7.10.8

当前的 Visual C# 编译器通过简单地检查引用是否相同来实现第一个(IL 实际上并不调用 mscorlib 方法,例如object.ReferenceEquals,但这会给出相同的结果),同时它通过调用实现第二个Delegate.op_Equality method http://msdn.microsoft.com/en-us/library/system.delegate.op_equality.aspx即使它是由 C# 语言规范定义的,它看起来也像是该程序集中的“用户定义”运算符,因此可能不是规范意义上的“用户定义”(?)。

请注意,§7.10.8 有点令人困惑,因为它说“每个委托类型隐式提供以下预定义的比较运算符”然后给操作员提供(System.Delegate, System.Delegate)签名。那只是one运算符,而不是“每种”委托类型的运算符?这对于我的问题似乎很重要。

前三名并不奇怪WriteLine write False, True and True,分别考虑到我上面所说的。

问题:


问题:但是为什么第四个 WriteLine 会导致使用 (object, object) 重载?

因为它是编译器的唯一选择:-)

Cannot apply operator '==' to operands of type 'System.Func<System.ICloneable>' and 'System.Func<System.IConvertable>'

候选人是:

bool==(System.Delegate, System.Delegate) 
bool==(System.Func<System.ICloneable>, System.Func<System.ICloneable>)
bool==(System.Func<System.IConvertable>, System.Func<System.IConvertable>)

因此,使用您的 (object, object) 是编译器找到的最佳选择。

动作也一样

Cannot apply operator '==' to operands of type 'System.Action<string>' and 'System.Action<System.Uri>'

候选人是:

bool==(System.Delegate, System.Delegate) 
bool==(System.Action<string>, System.Action<string>)
bool==(System.Action<System.Uri>, System.Action<System.Uri>)
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系:hwhale#tublm.com(使用前将#替换为@)

使用变体泛型委托类型对运算符 == 进行重载解析 的相关文章

  • 如何在C++中生成非常大的随机数

    我想使用 C 生成 0 2 64 范围内的非常大的随机数 我已经使用了 rand 函数 但它没有生成非常大的数字 有人可以帮忙吗 使用c 11 使用标准c 11的随机库 http en cppreference com w cpp nume
  • 在 WCF 上重用我的 PagedList 对象

    问题 我有一个自定义集合PagedList
  • 如何使用c#从数据桶中获取所有文档?

    如何获取数据桶中的所有文档 我尝试过一个示例 但我只能获得一个特定的文档 这是我的代码 CouchbaseClient oclient oclient new CouchbaseClient vwspace data bucket name
  • C++ 指针和对象实例化

    这有效 MyObject o o new MyObject 而这并不 MyObject o new MyObject Why 关键词new 返回一个指针 http msdn microsoft com en us library kewsb
  • 预编译头和 Visual Studio

    有没有办法设置 Visual Studio 解决方案参数 以便它只创建预编译头而不构建整个解决方案 具体来说 它是一个巨大的 C 解决方案 本身有许多项目 谢谢 仅选择 pch 创建者源文件 通常是 stdafx cpp 然后编译该文件 C
  • QSpinBox 输入 NaN 作为有效值

    我正在尝试扩展 QSpinBox 以能够输入 NaN 或 nan 作为有效值 根据文档 我应该使用 textFromValue valueFromText 和 validate 函数来完成此操作 但我无法让它工作 因为它仍然不允许我输入除数
  • FluentAssertions ShouldNotThrow 无法识别异步方法/Func

    我正在尝试检查异步方法是否抛出具体异常 为此 我使用 MSTEST 和 FluentAssertions 2 0 1 我已经检查过这个关于 Codeplex 的讨论 http fluentassertions codeplex com wo
  • std::make_pair 与浮点数组(float2,无符号整数)

    我有一个用 float2 unsigned int 对模板化的向量 例如 std vector
  • 原子存储抛出错误

    我最近升级到了 C 11 兼容编译器 并且尝试将一些代码从 boost 更新到 c 11 标准 我在使用atomic store转换一些代码时遇到了问题 这是一些简单的测试代码 似乎会引发编译器错误 int main std shared
  • asp.net core http 如果没有内容类型标头,则删除 `FromBody` 忽略

    我在 http 中使用 bodyDELETE要求 我知道目前删除主体是非标准的 但是允许的 使用时出现问题HttpClient它不允许删除请求的正文 我知道我可以使用SendAsync 但我宁愿让我的 API 更加灵活 我希望这个机构是可选
  • ASP.NET MVC 动作过滤器

    有谁知道即使在 CATCH 块中 ActionFilterAttribute 类的 OnResultExecuted 方法是否也会执行 ie CookiesActions public ActionResult Login Usuarios
  • 如何在 C++ 运行时更改 QML 对象的属性?

    我想在运行时更改 QML 对象的文本 我尝试如下 但文本仍然为空 这是后端类 class BackEnd public QObject Q OBJECT Q PROPERTY QString userFieldText READ userF
  • 从 C# 调用时无法识别 Powershell 命令

    这是这个的延续Question https stackoverflow com questions 66280000 powershell object returns null 66280138 noredirect 1 comment1
  • 调试错误:在 vc++ 项目中使用 COM 时发生 所需的运行时?

    我为我的工作创建了一个 COM 组件 我也注册了该组件 在我的系统上 我有两个虚拟机工作站 在我的第一个工作站中 它运行良好 在我的第二个工作站中 它显示一个包含消息的错误框该程序需要一段时间并以不寻常的方式关闭 请联系应用程序管理员 我认
  • 如何释放字符串未使用的容量

    我正在程序中处理很多字符串 这些字符串数据在读入我的程序后的整个生命周期内都不会改变 但由于 C 字符串保留了容量 因此浪费了大量肯定不会被使用的空间 我尝试释放这些空间 但没有成功 以下是我尝试过的简单代码 string temp 123
  • 展开 std::reference_wrapper 的成本

    Given include
  • Unity - 在生成时获取随机颜色

    我有一个小问题 我想在我的场景中生成四边形 它们都应该有红色或绿色作为材质 但 Random Range 函数只能是 int 我该如何解决它 void SpawningSquadsRnd rndColor 0 Color red rndCo
  • C# PasswordDeriveBytes:似乎 Salt 并不重要

    可能我误解了什么 以下代码通过 CryptDeriveKey 使用两种不同的盐生成两个相等的密钥 这是控制台结果 盐1 21 3e 18 a3 9a 8b 5f gt 键 da 89 ea 3d 91 08 20 98 20 e9 dc 4
  • Asp.Net Core 中的 SSL 不起作用

    我从 Visual Studio 创建了一个简单的 Web 应用程序Web Application Net Core 具有个人用户帐户授权的模板 然后 我启用了 SSLProject gt MyProject Properties 将带有
  • 创建进程默认浏览器

    我目前正在使用 ShellExecute 打开 在用户浏览器中打开 URL 但在 Win7 和 Vista 中遇到了一些麻烦 因为该程序作为服务运行提升 我想获取线程 id 因此 ShellExecute 无法获取线程 id 因此我开始使用

随机推荐