使用virtual覆盖方法签名

ami*_*han 2 c#

众所周知,对类中的方法使用virtual关键字允许我们在派生的子类中覆盖它.但是,方法仍然必须坚持相同的签名,例如返回值,参数等.

问题:在C#中,我怎样才能覆盖签名?这可能吗?

谢谢.

Jim*_*elo 5

这不可能.但是,如果需要,可以创建重载.

编辑

为了反对new,请考虑你有一个基础对象的情况,以及一个继承它的情况.通过放置new您尝试"更改"方法签名的方法之前,您实际上浪费了四个关键笔划.

public class Base {
    public string Foo () { return null; }
}

public class Inherited : Base {
    public new int Foo () { return 0; }
}
Run Code Online (Sandbox Code Playgroud)

现在,Inherited有两种方法:

public string Foo () { return null; }
public int Foo () { return 0; }
Run Code Online (Sandbox Code Playgroud)

您实际上并未更改方法签名.因此,new甚至不需要关键字.没有它你会得到同样的效果:

public class Inherited : Base {
    public int Foo () { return 0; }
}
Run Code Online (Sandbox Code Playgroud)

使用newis来覆盖基类的非虚拟成员:

public class Base { 
    public string Foo () { return null; }
}

public class Inherited : Base {
    public new string Foo () { return "Something else..."; }
}
Run Code Online (Sandbox Code Playgroud)

但如果你不注意这个微妙之处,你会遇到问题.随着virtual您获得一个虚拟查找表,将您的功能映射到正确的调用.有new,你不会.如果你传入需要Inherited一个Base对象的地方(这当然会起作用),那么将调用这个BaseFoo()!不,Inherited"覆盖" Foo().

这与覆盖虚拟成员的行为不同.

public static class MyClass {
    public string MyMethod (Base @base) {
        return @base.Foo ();
    }
}

[Test]
public void then_it_should_return_non_null () {
    var obj = new Inherited ();
    var result = MyClass.MyMethod(obj);  // obj will get upcasted to Base
    Assert.That (result, Is.EqualTo(obj.Foo ())); // Assert fails!
}

[Test]
public void inherited_should_return_correct_value ()
{
    var obj = new Inherited ();
    var result = obj.Foo ();  // will access the "new" method, hiding Base's implementation
    Assert.That (result, Is.Not.Null);  // Assert passes! 
}
Run Code Online (Sandbox Code Playgroud)