如何覆盖泛型方法?(C#)

时间:2009-01-30 13:21:29

标签: c# .net collections

我正在创建一个名为TetraQueue的类,它继承了覆盖System.Collections.Generic.Queue方法的Dequeue类,这里是代码:

public class TetraQueue : Queue<Tetrablock>
{
   public override Tetrablock Dequeue()
   {
       return base.Dequeue();
   }
 }

但是当我尝试编译时,我得到了:

  

错误TetraQueue.Dequeue()':找不到合适的方法来覆盖TetraQueue.cs

提前致谢。

我怎么知道方法是否是虚拟的(避免这种情况)?

7 个答案:

答案 0 :(得分:9)

了解方法是否为虚拟的两种方法:

  • 在Visual Studio中键入“override” - 它将为您提供允许覆盖的所有方法。
  • View the documentation - Dequeue并不是说它是虚拟的,所以你不能覆盖它。

编辑:其他人建议隐藏该方法。我强烈建议你这样做,除非你真的,真的必须这样做。当继承出现有时可以工作时,这是困难的调试会话和挫折的一个方法,有时不工作,具体取决于引用的编译时类型。 Blurgh。如果您不打算专门化这种行为,请使用合成而不是继承。

答案 1 :(得分:5)

您必须使用关键字。这将告诉编译器您希望将此方法放在另一个上面。但是只是警告,如果你使用Queue这样的基类,你将无法使用这种新方法。

public class TetraQueque : Queue<Tetrablock>
{
   public new Tetrablock Dequeque()
   {
       return base.Dequeue();
   }
}

答案 2 :(得分:3)

不幸的是,Dequeue方法不是虚拟的,因此您无法覆盖它。

答案 3 :(得分:1)

添加new关键字以隐藏基类上的方法。

关于.net:http://www.akadia.com/services/dotnet_polymorphism.html

中多态性的好文章

答案 4 :(得分:1)

队列没有Deque q ue方法,但是Dequeue方法。那将是第一个编译错误,如果你修复它,你仍然无法编译,因为它不是一个虚方法。

使用new关键字可以重新引入此方法,但请记住拼写正确的函数名称,否则会有.Dequeue.Dequeque方法。

问题本身也包含此拼写错误。

答案 5 :(得分:1)

覆盖一个只调用父节点的方法是没有意义的,所以如果你发布的代码就是你正在做的事情,那么就不要覆盖它。

让你的TetraQueue成为一个队列&lt; TetraBlock&gt;你说它可以在队列&lt; TetraBlock&gt;时使用。可。通过向它添加一个隐藏原始方法的新方法,如果调用者知道它的TetraQueue,那么你就是在弄乱那个合同。

如果我想要与Queue相同的行为,我会使用Queue&lt; TetraBlock&gt ;;如果我想要不同的东西,我会使用构图而不是继承。

答案 6 :(得分:1)

如前所述,您无法覆盖该方法,因为它是非虚拟的。但是,我强烈建议你不要隐藏这个方法。请考虑以下事项:

class Program
    {
        static void Main(string[] args)
        {
            A a = new A();
            B b = new B();
            A c = new B();

            // Straight A
            a.MyVirtualMethod();
            a.MyNonVirtualMethod();

            // Straight B
            b.MyVirtualMethod();
            b.MyNonVirtualMethod();

            // Polymorphic
            c.MyVirtualMethod();
            c.MyNonVirtualMethod();

            Console.ReadLine();
        }
    }

    public class A
    {
        public virtual void MyVirtualMethod()
        {
            Console.WriteLine("Hello world!");
        }

        public void MyNonVirtualMethod()
        {
            Console.WriteLine("Hello world!");
        }
    }

    public class B : A
    {
        public override void MyVirtualMethod()
        {
            Console.WriteLine("Good bye universe!");
        }

        public new void MyNonVirtualMethod()
        {
            Console.WriteLine("Good bye universe!");
        }
    }

对于不了解实现的人来说,此代码的输出并不明显。

Hello world!
Hello world!
Good bye universe!
Good bye universe!
Good bye universe!
Hello world!