virtual与new virtual有本质区别嘛?(警告会有不同,但不算本质区别)在多态的表现上,感觉上是一样的,
如果有区别,能给出反证嘛?
using System;namespace PCTest
{
    public class ClassB
    {
        public new virtual void GetName()
        {
            Console.WriteLine("GetName:ClassB!");
        }
    }    public class ClassBB : ClassB
    {
        public new virtual void GetName()
        {
            Console.WriteLine("GetName:ClassBB!");
        }
    }    public class ClassBBB : ClassBB
    {
        public new virtual void GetName()
        {
            Console.WriteLine("GetName:ClassBBB!");
        }
    }    //abstract|virtual|override|new|[]|new virtual|null
    //
    //abstract->override
    //virtual->[]|virtual|override|new virtual|override|new
    //[]->[](=new)|new|virtual|new virtual
    //override->[](=new)|new|virtual|new virtual|override
    //new->[](=new)|new|virtual|new virtual
    //new virtual->[]|virtual|override|new virtual|override|new
    //
    //abstract   :当前不实现,不覆写基类,不能被重写,  必须覆写
    //[]|new     :  当前实现,不覆写基类,  能被重写,不能被覆写,[]会有警告
    //virtual    :  当前实现,不覆写基类,  能被重写,  能被覆写,会有警告//
    //new virtual:  当前实现,不覆写基类,  能被重写,  能被覆写,会有警告//
    //override   :  当前实现,  覆写基类,  能被重写,  能被覆写
        public class Test
    {
        static void Main()
        {
            //建立对象
            ClassB a = new ClassB(); a.GetName();
            ClassBB aa = new ClassBB(); aa.GetName();
            ClassBBB aaa = new ClassBBB(); aaa.GetName();            //
            ClassB b;
            ClassB bb;            b = aa; b.GetName();
            b = aaa; b.GetName();
            bb = aaa; bb.GetName();            //End
            Console.ReadKey();
        }
    }
}

解决方案 »

  1.   

    如果你使用new,我会立马放弃。
      

  2.   

    呵呵,NEW还是不错的,主要用于版本控制。
    基于以下场景:
    A公司拥有ClassA
    B公司向A公司购买了ClassA
    B公司在ClassA的基础上实现了ClassB
    B公司在ClassB中增加了ClassA中没有的比如Sort方法并定义为virtual方法
    某天A公司的新版本中增加了Sort方法
    这时B公司就需将Sort方法改为new virtual方法btw1:C#一旦发现虚方法,就不去查看继承的层次,虚方法被当成虚拟分派(dispatch)。
    btw2:[]代表“方法”前没有修饰,NULL代表子类中没有“方法”(这个很容易理解,所以没有放进例子中)。
      

  3.   

    一个是virtual, 一个是新new virtual,重写与履盖的区别 
      

  4.   

    你的问答不对,应该是这样:
    一个是virtual, 一个是新new,重写与履盖的区别
      

  5.   

    new virtual 是隐藏了基类的同名方法,同时说明该类的派生类可以重写该方法。
      

  6.   


    那virtual呢,
    从表现上,同样是隐藏了基类的同名方法.我们需要了解是两者是区别
      

  7.   

    那virtual呢, 
    从表现上,同样是隐藏了基类的同名方法. 
    -------------------------------
    看来你对virtual的理解还有问题:virtual 关键字用于修饰方法、属性、索引器或事件声明,并使它们可以在派生类中被重写。
    虚拟成员的实现可由派生类中的重写成员更改。
      

  8.   

    你可以这样的理解:virtual:
    virtual 关键字用于修饰方法、属性、索引器或事件声明,并且允许在派生类中重写这些对象。例如,此方法可被任何继承它的类重写。(自MSDN)
    而与virtual对应的为override,重写其父对象里的方法
    给你举下例吧class a{
       public virtual void say{
           Console.WriteLine("这里是aa!");
       }
    }
    class b:a{
       public override void say{
           Console.WriteLine("这里是bb,aa被替换了!");
       }
    }
    class c:a{
       public override void say{
           Console.WriteLine("这里是cc,aa被替换了!");
       }
    }那么:
    a _a = new b();
    _a.say();//打印出,这里是bb,aa被替换了

    new:(摘自MSDN)
    在用作修饰符时,new 关键字可以显式隐藏从基类继承的成员。隐藏继承的成员意味着该成员的派生版本将替换基类版本。在不使用 new 修饰符的情况下隐藏成员是允许的,但会生成警告。使用 new 显式隐藏成员会取消此警告,并记录代之以派生版本这一事实。
    若要隐藏继承的成员,请使用相同名称在派生类中声明该成员,并使用 new 修饰符修饰该成员。public class BaseC 
    {
        public int x;
        public void Invoke() {}
    }
    public class DerivedC : BaseC
    {
        new public void Invoke() {}
    }
    在此示例中,DerivedC.Invoke 隐藏了 BaseC.Invoke。字段 x 不受影响,因为它没有被类似名称的字段隐藏。 
    对同一成员同时使用 new 和 override 是错误的,因为这两个修饰符在含义上相互排斥。使用 new 会用同样的名称创建一个新成员并使原始成员变为隐藏的,而 override 则扩展继承成员的实现。
      

  9.   


    同样感谢gjl370825对virtual的解释!!!我们现在要讨论的不是virtual有什么用处(所括override)
    (好象大家都是冲着这个来的,不客气的说,这个只是初级阶段,如果不了解virtual和override的用法,就不能把握多态的性质)而是能够说清楚virtual与new virtual的"本质"区别.
      

  10.   


    我知道你问得什么了。
    在派生类中 你写new virtual和virtual没有任何区别,两者都是隐藏基类同名方法,只不过后者有一个警告而已。这和一般的 new methordname和methordname一样。
      

  11.   

    避免用new 用new很容易出BUG的
    当你不得不用new的时候,你的OO设计就已经出问题了
      

  12.   

    logxing 说的不错,我是想确认一下。其实可以这样来看待 new 的作用void fun()
    new void fun()virtual fun()
    new virtual void fun()这两组修饰的区别在于new是经过了"显式"的确认,在重写时不出现警告。
    如果去除new的确认功能,我们更可以理解为new其实没有产生对多态的影响作为。
    而单独的new远全可以当作无修饰,
    这样的话,这七种修饰关系就相当容易理解了。tabbycat 的观点不认同
    首先new是非常必要的,有确认的功能(这个不针对你的问题)
    其次new有版本控制的作用,我在3楼给出了一些解释对以下七种修饰作一个总结:
    |virtual|override||[]|new virtual|null
    --------
    new:特殊的确认作用(注意:这样解释仅仅是为了便于理解)
    null(没有函数):自然继承
    abstract:比较好理解
    --------
    []:重写
    override:
    virtual=new virtual=[]+override另:在多态的理解上,要注意对象的两个状态
    ClassB a = new ClassBB();
    (一)变量的类型ClassB
    (二)对象的类型ClassBB
    其规则是:C#一旦发现虚方法,就不去查看继承的层次,虚方法被当成虚拟分派(dispatch)
      

  13.   

    再补充一点:
    virtual与new virtual,
    除了警告上的差异,
    还是存在一些“本质性”的小区别。我会在新开贴中加以阐述
    新贴:关于"继承"与"多态"的关系,我们到底理解了有多少.
    http://topic.csdn.net/u/20090805/13/254df2c5-2356-438a-a7f5-7f9ce5a9b3b0.html
      

  14.   

    Class A
    Class B:AA中有一个方法,B继承了A中的方法,但不想实现A中的方法,他可以直接修改里面的方法,但在B中方法的下面会出现一条警告波浪线,,,这时,可以在B类的方法前面加上 new  就可以轻松解决,,,,,也可以在A类中的方法前面加上 virtual 在B类方法中加上 override 也可以轻松解决~!~!希望能有帮助~!