今天我们来谈谈C#中子类和父类中静态成员以及构造函数的执行顺序,这个地方向来是初学C#的人比较迷惑的地方,也是各大公司最喜欢拿来出面试题的地方。

下面我们分情况来分析。

1. 普通构造函数和静态构造函数的执行顺序。

对于单个的类,它的静态构造函数将先于普通构造函数执行,因为普通构造函数需要在实例化该类的时候执行,而静态构造函数访问该类的同时就开始执行。

而对于有继承关系的父类和子类来说,父类的普通构造函数先于子类的普通构造函数执行,简而言之就是被依赖的先构造,依赖于人的后构造。

我们来看实例。

我们为父类和子类分别定义静态构造函数和普通构造函数。

public class Parent
{
static Parent()
{
Console.WriteLine("Parent Static Constructor");
}
public Parent()
{
Console.WriteLine("Parent Constructor")

}

}

定义一个子类继承于该父类。

public class Child : Parent
{
static Child()
{
Console.WriteLine("Child Static Constructor");
}
public Child()
{
Console.WriteLine("Child Constructor");
}

}

那么当我们实例化Child类的时候会如何输出呢?

static void Main(string[] args)
{
Child child = new Child();
Console.Read();
}

结果如下

这个结果很好解释,我们实例化子类,所以静态构造函数在访问类的时候同时访问,所以先执行子类的静态构造函数,而Child类依赖于Parent类,所以接下来执行Parent类的普通构造函数。

两个类的静态构造函数执行完毕后分别执行父类的普通构造函数和子类的普通构造函数。

2. 静态变量,静态构造函数以及普通构造函数的情况。

从上面分析的第一种情况我们知道静态构造函数是先于普通构造函数执行的, 而静态变量是先于静态构造函数执行的。

那如果该静态变量定义的是该类的一个实例执行顺序如何呢?

我们来看实例。

public class Child
{
static public Child instance = new Child();
static Child()
{
Console.WriteLine("Child Static Constructor");
}
public Child()
{
Console.WriteLine("Child Constructor");
}

}

实例化该类,显示结果如下:

对于这个执行结果,首先执行的是静态变量,而该静态变量是对Child类的实例化,此时先调用它的普通构造函数,为什么不会调用它的静态构造函数呢?因为静态构造函数的执行在静态变量之后,

所以第一步,初始化静态变量,打印 "Child Constructor" ;

第二步,执行静态构造函数,打印 "Child Static Constructor" ;

第三步,执行普通构造函数, 打印 "Child Constructor".

3. 存在继承关系的静态变量,静态构造函数,普通构造函数的执行顺序.

下面我们把第二种情况复杂化一点,加入父类。

public class Parent
{
static Parent()
{
Console.WriteLine("Parent Static Constructor");
}
public Parent()
{
Console.WriteLine("Parent Constructor");
}

}

子类继承于父类。

public class Child :Parent
{
static public Child instance = new Child();

static Child()
{
Console.WriteLine("Child Static Constructor");
}
public Child()
{
Console.WriteLine("Child Constructor");
}

}

如果我们实例化Child类,会产生什么结果呢?在我给出答案之前,大家不妨先分析一下这个结果。

1. 先初始化Child类的静态变量instance。

显然最开始执行的是Child类中的静态变量instance,instance要实例化一个Child类,那么首先要访问Child类的普通构造函数,而Child类又是依赖于Parent类的,所以在执行Child类的

构造函数之前,先执行的是它父类的静态构造函数和普通构造函数(注意此时Child类的静态构造函数不会执行)。它将打印出"Parent Static Constructor"和"Parent Constructor".

其次执行这个普通构造函数,(此时Child类的静态构造函数仍然不会执行)。打印出"Child Constructor".

2. 执行Child类的静态构造函数

这次将打印出"Child Static Constructor"。

3. 执行Child类的普通构造函数

执行Child类的普通构造函数,这里会产生两个结果。首先,会执行它父类的普通构造函数,注意此时父类的静态构造函数不会执行了,它只会执行一次。其次才是执行Child类自己的普通构造函数。

因此此时应该打印出"Parent Constructor"和"Child Constructor".

实际运行的结果也证明刚才分析的正确性。

通过上面三个例子的分析,相信大家应该知道了如何去分析这个执行顺序,那就给大家留一个作业自己思考吧。

父类:

public class Parent
{
static public Parent instance = new Parent();

static Parent()
{
Console.WriteLine("Parent Static Constructor");
}
public Parent()
{
Console.WriteLine("Parent Constructor");
}

}

子类:

public class Child :Parent
{
static public Child instance = new Child();

static Child()
{
Console.WriteLine("Child Static Constructor");
}
public Child()
{
Console.WriteLine("Child Constructor");
}

}

}

http://www.cnblogs.com/ustbwuyi/archive/2011/03/25/1994989.html

转载于:https://blog.51cto.com/flydragon0815/669761

谈谈C#中类成员的执行顺序.相关推荐

  1. Java类中各成员的执行顺序

    属性.方法.构造方法和自由块都是类中的成员,在创建对象时,各成员的执行顺序如下: (1)父类静态成员和静态初始化块,按在代码中出现的顺序依次执行. (2)子类静态成员和静态初始化块,按在代码中出现的顺 ...

  2. java静态代码块、静态方法、静态变量、构造代码块、普通代码块、成员变量执行顺序

    package smartt.styy.auth.model.voRsp;public class Test {static {String test5="555";//局部变量t ...

  3. java静态/动态成员变量、初始化块,父类/子类构造函数执行顺序问题

    2019独角兽企业重金招聘Python工程师标准>>> /* * 几大原则 * 一.静态成员变量(Static) * 1.静态成员变量为类变量,所有对象共享同一内存空间 * 2.静态 ...

  4. java中类的加载及执行顺序

    为什么80%的码农都做不了架构师?>>>    类的加载顺序  什么时候类加载  第一次需要使用类信息时加载.  类加载的原则:延迟加载,能不加载就不加载. 触发类加载的几种情况:  ...

  5. java 类的执行顺序_Java中类的执行顺序

    讲解在代码中: package 类执行顺序; /** * java类执行顺序 * * 1.如果父类有静态成员赋值或者静态初始化块,执行静态成员赋值和静态初始化块 * 2.如果类有静态成员赋值或者静态初 ...

  6. C++中类成员变量在初始化列表中的初始化顺序

    引子:我们知道,C++中类成员变量的初始化顺序与其在类中的声明顺序是有关的. 先看代码: 1 class TestClass1 2 { 3 public: 4 TestClass1() { 5 cou ...

  7. Java中类的执行顺序

    目录标题 变量的分类 按数据类型分类 按声明的位置分类 成员变量 (属性)VS 局部变量 类变量(静态变量) 常量 JVM一个类的加载过程? 一个类被初始化的过程? 创建一个对象时,发生了什么. 1. ...

  8. java变量,初始化快,构造函数的执行顺序

    转自 http://blog.csdn.net/macheng365/article/details/6403050 ----------------------------------------- ...

  9. 面向对象(二)构造函数,this,static,类的成员,对象初始化顺序

    点击查看好文 TestCode package com.openlab.day10.object;public class Test {public static void main(String[] ...

最新文章

  1. 都啥时候了,你还怕学了Python找不到工作?
  2. Integer to Roman 问题
  3. C语言 main 函数到底为啥这么写?
  4. java项目:永和大王项目_Java项目:书评
  5. c++ 使用未初始化的内存_C语言内存分布(内核区、堆栈区等)
  6. 深入理解l内核v4l2框架之video for linux 2(转载)
  7. 学用MVC4做网站五:5.4删除文章
  8. Linux 命令tar的简单用法
  9. 计算机操作系统汤小丹版课后答案
  10. Scala基础入门(二) Scala下载、安装教程
  11. 查看Eclipse的工作路径
  12. ffmpeg 中av_rescale_rnd 的含义
  13. 偷用计算机作文,【实用】《偷着》作文500字4篇
  14. 数据泵并行parallel参数问题
  15. Chrome 改进 Enhanced Safe Browsing 功能,强化扩展程序和文件下载安全性
  16. 【JS】对象数组去重+查重+合并同类项
  17. 12、Zabbix 结合Grafana
  18. 十二步解N-S方程之第四步
  19. 文件传输协议(FTP)
  20. ES5、ES6和ES2015有什么区别?

热门文章

  1. 不需xp_cmdshell支持在有注入漏洞的SQL服务器上运行CMD命令
  2. Hessian通信案例(java)
  3. C语言数据类型所占空间大小
  4. Gin源码解析和例子——中间件(middleware)
  5. CUDA Samples: green ball
  6. 【Go】Go基础(六):数组、切片slice、映射map
  7. 计算机专业期末考试是编程序,计算机专业技能期末考试题
  8. php 生成动态键值 数组_你的PHP项目遇到性能问题了吗?看完这篇性能分析恍然大悟...
  9. Java学习总结:4
  10. Java项目:网上商城系统(java+jsp+servlert+mysql+ajax)