C# 签名相同的代表

C# 签名相同的代表,c#,.net,oop,delegates,clr,C#,.net,Oop,Delegates,Clr,我的问题有点类似于这个: 为什么具有相同签名的代理之间没有隐式转换。例如,代码: class Program { private delegate void Foo1(int x); private delegate void Foo2(int x); static void Main(string[] args) { Foo1 foo1 = Console.WriteLine; Foo2 foo2 = Console.Writ

我的问题有点类似于这个:

为什么具有相同签名的代理之间没有隐式转换。例如,代码:

class Program
{
    private delegate void Foo1(int x);
    private delegate void Foo2(int x);


    static void Main(string[] args)
    {
        Foo1 foo1 = Console.WriteLine;
        Foo2 foo2 = Console.WriteLine;

        Call(foo1);

        Call2(foo2);
    }

    static void Call(Action<int> action)
    {
        action(10);
    }

    static void Call2(Foo1 action)
    {
        action(10);
    }
}
类程序
{
私人代表1(整数x);
私人代表2(整数x);
静态void Main(字符串[]参数)
{
Foo1 Foo1=Console.WriteLine;
Foo2 Foo2=Console.WriteLine;
电话(foo1);
Call2(foo2);
}
静态无效调用(操作)
{
行动(10);
}
静态无效调用2(Foo1操作)
{
行动(10);
}
}
它不会编译,因为没有从Action到Foo1的隐式转换。 但正常情况下是一样的。这意味着这些名字是别名,而不是真正的名字。所以我认为把它当作别名来考虑是个好主意。因此,在本例中,我们有一个
委托的3个别名,它得到一个int值,但不返回任何内容。这些代表完全可以相互替换。但我们没有。所以问题是:为什么?通过签名,这是同一件事,并且没有任何实现,因此具有相同签名的代理是一个相同的代理,有许多别名


是C#缺陷还是有原因?至于我,我没有看到任何。这两个代理之间没有隐式转换,原因与这两种类型之间没有隐式转换相同:

public sealed class Foo1
{
    public string Value { get; set; }
}

public sealed class Foo2
{
    public string Value { get; set; }
}
仅仅因为两个类具有相同的字段并不意味着您可以将一个类当作另一个类来处理。同样的逻辑也适用于委托(请注意,委托也是类型)

该类型的创建具有语义意义。如果有人创建了
Foo1
,他们希望它是
Foo1
,而不是
Foo2
。如果他们特意使用
Foo1
而预期使用
Foo2
,这是一个巨大的危险信号,即尽管类型看起来相似,但这两种类型之间存在语义差异。如果程序员知道编译器不知道的东西,他们可以使用某种显式转换来表明他们知道自己在做什么


(前一段是故意写的,同样适用于你的代表和我上面提供的课程)

我不认为这是个人的缺陷,但这就是为什么当人们定义自己的代表而不是仅仅使用<代码>动作< /COD> >代码> FUNC> /代码>时,我会感到恼火。类可以是部分的,也可以是继承的,等等。例如,我有行动。我不想写关于它是什么的简单/XML注释,我可以简单地写一些类似于
MySpecialDelegate=Action
的东西,它只是一个自我记录的代码。对于类来说,它可能是一个很好的函数,但是对于它们来说,它不会经常被使用,因为这两个类几乎总是不一样的,但是委托是一样的。当我使用MyAlarmTimer=System.Timers.Timer编写
时,我不是说“一个大的危险信号”,我只是想简化一些代码,并且不加注释地解释一下为什么我不能在这里做同样的事情-我不知道。就像在本例中,它只是一个别名,对于运行代码来说,它们之间没有区别。如果.Net中的所有代理都可以自动转换为Action/Func,那将非常有用nice@AlexJoukovsky并非所有具有相同签名的方法都是相同的。很可能这个方法的语义对它的影响更大。您可能不会使用不同的委托来附加语义,但这并不意味着没有人这样做,也不意味着语言设计者认为不应该这样做。至于课程是部分的,这不是真的相关;一旦它们被编译器编译,它只是一个类定义。至于继承,可以封存;如果这能让你感觉更好的话,我会在我的例子中加上“不是所有具有相同签名的方法都是相同的”。他们有相同的签名!这听起来像是“两个人,有着相同的名字,第二个名字和姓氏,同样的罪,但有着不同的昵称,不是同一个人”@AlexJoukovsky首先,这些方法不需要有相同的名字。其次,仅仅因为两个人的名字相同并不意味着他们是同一个人。你认为所有具有相同签名的方法都做相同的事情……我甚至不知道该怎么说。你写过多少不接受参数也不返回值的方法?他们都做了同样的事吗?