using System;
   class A
   {
  public A()
  {
   PrintFields();
  }
   
  public virtual void PrintFields()
  {
   
  }
   }   class B:A
   {
    int x=1;
    int y;    public B()
    {
   y=-1;
    }
    
    public override void PrintFields()
    {
   Console.WriteLine("x={0},y={1}",x,y);
    }
 }当使用new B()创建B的实例时,产生什么输出?答:x=1,y=0。为什么是1 0呢 B b=new B();//1 0 这里Y是附值的呀。值呢。。
b.PrintFields()//这里为什么又是1 -1了呢?
55555头大的不行了帮帮吧 大大们~~!!!

解决方案 »

  1.   

    B b=new B();//1 0 这里Y是附值的呀。值呢。。
    --> new的时候 先给父类成员变量分配空间(此题无),再给子类成员变量分配空间(x = 1, y = 0)
    再调用父类无参构造,此时父类构造里调用了PrintFields方法,此方法又被子类重写,考虑到方法的动态绑定,故调用的是子类的方法,而此时 x = 1, y = 0;最后调用父类的构造函数,这个时候才给 y  赋值为 -1的。
    b.PrintFields()//这里为什么又是1 -1了呢?这里为什么是 1 -1 就不用再说了,接着上边的。
      

  2.   

    public override void PrintFields()
      {
      Console.WriteLine("x={0},y={1}",x,y);
      }
    这段代码执行在赋值之前,当然应该是这个结果了!你调试下看看。
      

  3.   

    new b的时候由于b是继承a,所以会先执行a的构造函数
      

  4.   

    谢谢 keeya0416 我懂了 呵呵 
      

  5.   

    子类在初始化的时候会先调用父类的构造方法。步骤如下。
    1。实例化B
    2。检查B是否存在父类(必存在,原因所有类都源自object)
    3。调用父类构造方法。
    3。如果方法中调用了其他成员方法则执行
    4。检查成员方法是否被重写,如果重写则调用重写后的方法。
    5。调用返回后再调用本身的构造方法。
    给出代码。using System;
    using System.Collections.Generic;
    using System.Linq;
    using System.Text;
    using System.Data;namespace MergeTest
    {
        class Program
        {
            static void Main(string[] args)
            {
                B b = new B();
            }
            class A
            {
                public A()
                {
                    PrintFields();
                }            public virtual void PrintFields()
                {
                    Console.WriteLine("Base Method");
                }
            }        class B : A
            {
                int x = 1;
                int y;            public B()
                {
                    y = -1;
                    base.PrintFields();//调用父类方法
                    PrintFields();//调用自己方法
                }            public override void PrintFields()
                {
                    Console.WriteLine("x={0},y={1}", x, y);
                }
            }
        }
    }
      

  6.   

    你可以F11跟踪一下 
    你会发现
    执行B的构造函数前 先构造A
    然后执行A.PrintFields(),在这里跳至B.PrintFields()
    在这个时候 x=1,y是编译器赋的默认值 0 
    所以打印出 x=1,y=0。再继续往下 
    才真正的进入到B的构造函数 ,最后才执行B.PrintFields()
    这里的时候 y值已经在B的构造函数中被重新赋值 y=-1;所以结果为 :x=1,y=-1。最终结果:
    x=1,y=0;
    x=1,y=-1