在类的继承和多态中对实例化顺序和方法重写用法的一些总结

  总结一下使用类继承和多态时,实例化顺序以及方法继承重写中new,virtual、abstract、override的用法和规则:

  继承关系:实例化对象时,作用类型范围在最初基类到具体实例对象的类之间(中间包括父类子类,成员访问权限:private、protected、public):

  1、 子类实例构造器必须指定拥有父类访问权限的实例构造器:base(xxx),不写默认父类无参构造器;使用:this(xxx)指定先运行本类的某实例构造器,再由他指定执行的父类实例构造器;

  2、 先实例化基类,再实例化子类,再子类的子类....最后到要实例的类(实例构造函数执行顺序先父后子...;期间加载时遇到有静态构造器就会先运行静态构造器,再到指定的实例构造器按顺序规则执行,静态构造器只在加载时执行一次,执行过就会跳过);

  3、 在运行方法时,就运行当前所属类型中的方法:

     1).当遇到隐藏new方法时(实际上C#中使用签名隐藏,只要方法名字和参数相同就会隐藏而new只是消除编译器警告罢了),说明子类方法为全新方法与父类不具重写关系,仍然运行当前所属类型中的方法;

     2).当遇到虚virtual、抽象abstract、继承覆盖override方法时,说明方法具体实现已重写,就运行离具体对象类型关系最近的一个类的重写方法。当然关系最近的是自身。

  最后例子说明一下:

  这里提一下:抽象类无法直接实例化即不能显式调用构造器(new,反射),需要借助子类实例化时,构造函数调用抽象类的构造函数如:base()进行实例化,就是为继承和重写而生的抽象实例成员只能放在抽象类中;静态类只能有静态成员(包括构造函数),不能显式调用构造器,初始加载时系统通过构造函数自动创建一个静态对象。

 1     public abstract class A
 2     {
 3         public int x;
 4         public A()
 5         {
 6             x = -1;
 7             Console.WriteLine("x={0}", x);
 8             Print1();
 9             Print2();
10         }
11         public virtual void Print1() 
12         {
13             x = 1;
14             Console.WriteLine("x={0}", x);
15         }
16 
17         public virtual void Print2() 
18         {
19             x = 2;
20             Console.WriteLine("x={0}", x);
21         }
22     }
23 
24     public class B : A
25     {
26         public int y;
27         public B()
28         {
29             y = -1;
30             Console.WriteLine("x={0},y={1}", x, y);
31             Print1();
32             Print2();
33         }
34 
35         public override void Print1()
36         {
37             x = 3;
38             y = 1;
39             Console.WriteLine("x={0},y={1}", x, y);
40         }
41         //该方法将继承的重新创建,自身及其后子类重写均为这个方法
42         public new virtual void Print2()
43         {
44             x = 4;
45             y = 2;
46             Console.WriteLine("x={0},y={1}", x, y);
47         }
48     }
49     public class C : B
50     {
51         //该方法将继承的重新创建,自身及其后子类继承的均为这个方法
52         public new void Print1()
53         {
54             x = 5;
55             y = 3;
56             Console.WriteLine("x={0},y={1}", x, y);
57         }
58         //该方法重写自父类B,而不是基类A
59         public override void Print2()
60         {
61             x = 4;
62             y = 2;
63             Console.WriteLine("x={0},y={1}", x, y);
64         }
65     }
66     public static class D
67     {
68         public static string _name;
69         static  D()
70         {
71             _name = "小明";
72         }
73     }
View Code

  主程序:

 1         static void Main(string[] args)
 2         {
 3             A c = new C();
 4             c.Print1();
 5             c.Print2();
 6             //静态、抽象类反射不能创建
 7             //Type type = typeof(A);
 8             //var constructor = type.GetConstructor(Type.EmptyTypes);
 9             //Object obj = constructor.Invoke(null);
10             //Console.WriteLine(obj.GetType().Name);
11             //Type type = typeof(D);
12             //var constructor = type.GetConstructor(BindingFlags.Static|BindingFlags.NonPublic,null,Type.EmptyTypes,null);
13             //Object obj = constructor.Invoke(null);
14             //Console.WriteLine(obj.GetType().Name);
15             Console.WriteLine(D._name);
16             Console.ReadKey();
17         }
18         
View Code

  输出结果:

posted @ 2021-01-23 16:33  JN-SHao  阅读(76)  评论(0编辑  收藏