惯性聚合 高效追踪和阅读你感兴趣的博客、新闻、科技资讯
阅读原文 在惯性聚合中打开

推荐订阅源

WordPress大学
WordPress大学
小众软件
小众软件
钛媒体:引领未来商业与生活新知
钛媒体:引领未来商业与生活新知
博客园 - Franky
Jina AI
Jina AI
freeCodeCamp Programming Tutorials: Python, JavaScript, Git & More
OSCHINA 社区最新新闻
OSCHINA 社区最新新闻
Y
Y Combinator Blog
V
Visual Studio Blog
C
Check Point Blog
阮一峰的网络日志
阮一峰的网络日志
U
Unit 42
量子位
人人都是产品经理
人人都是产品经理
博客园 - 聂微东
M
MIT News - Artificial intelligence
爱范儿
爱范儿
B
Blog RSS Feed
MyScale Blog
MyScale Blog
H
Help Net Security
Cyber Security Advisories - MS-ISAC
Cyber Security Advisories - MS-ISAC
美团技术团队
L
LangChain Blog
D
Docker

博客园 - xwang

更好的执行 Better Communication – 你在听吗? 时间管理 or 能量管理 Stress Managment - 压力管理 Understanding WPF Template 调试Rotor: 启动过程 sscli google group launched 自定义Rotor: 给Rotor添加一个CIL指令 PAL 阅读笔记 Metadata Tables, 元数据表 [Coding For Fun] 您有运行许可证吗? How To: TeamBuild 编译之前的版本 How To: Team Build 自定义版本号 混淆的概念与实践 [Debugging Tool]Windbg调试托管代码 The Anatomy Of Basic Data Structure, 基本数据结构解析 Understanding GetHashCode, 理解GetHashCode 基本数据结构解析之List 试探讨泛型实现过程
Understanding Static Constructor, 理解静态构造函数 - xwang
xwang · 2009-01-06 · via 博客园 - xwang

引言:

想起这个问题是一次面试提到的题目而起,而之前也有关于静态构造函数和构造函数区别, 于是有了这次探索.

用法:

1. 初始化静态成员数据

   1: public class MyTest
   2: {
   3:     static string Str = "This is MyTest";    
   4:     static int i = 0;
   5:  
   6:     static MyTest()
   7:     {
   8:         Str = "Hi, I am Initialized";
   9:         i++;            
  10:     }
  11: }

2. 初始化静态readonly成员

   1: public class MyTest
   2: {
   3:     static readonly string MyReadonlyData = "MyTest's MyReadonlyData";
   4:     
   5:     static MyTest()
   6:     {
   7:         MyReadonlyData = ":), Has been modifyed in static contructor";    
   8:     }
   9: }

实现层次:

对应的il代码结构, 所谓cctor, 是类中定义初始化数据的方法

image

在.Net对于赋值操作又分为两种方式

  1. precise
  2. beforefieldinit

precise 执行方式

   1: public class AnotherTest
   2: {
   3:         static AnotherTest() {
   4:  
   5:         }
   6:         public static string Test = "This is a test from another test";
   7: }

beforefieldinit

   1: public class AnotherTest
   2: {
   3:     public static string Test = "This is a test from another test";
   4: }

所谓beforefieldinit是指在数据被调用前初始化数据.

image

至于il代码,也是在class定义时添加了一个beforefieldinit标记, 在初始化数据时于是我们建议使用constructor chain来初始化数据,所谓constrcutor chain:

   1: namespace XWang
   2: {
   3:     public class Test
   4:     {
   5:         int A;
   6:         int B;
   7:         int C;
   8:         string InitialConfigurations;
   9:     
  10:         // The Constructor to initialize the private datas
  11:         public Test()
  12:         {
  13:             B = 2;
  14:             C = 3;
  15:         }
  16:  
  17:         // Initalize the a and call the default parameterless constructor
  18:         public Test(int a) : this()
  19:         {
  20:             A = a;
  21:         }
  22:  
  23:         // A Constructor Chain to initialize the datas
  24:         public Test(string configuration, int a): this(a)
  25:         {
  26:             InitialConfigurations = configuration;
  27:         }        
  28:     }
  29: }

对于静态构造函数,我们也应该在静态构造函数中初始化数据

   1: namespace XWang
   2: {
   3:     public class StaticConstructorTest
   4:     {
   5:         static string StaticData;
   6:  
   7:         static StaticConstructorTest()
   8:         {
   9:             StaticData = "Hi, I am initialized";
  10:         }
  11:     }
  12: }

同时这也是Effective C#中提到的其中几个原则:

  • 条款12:变量初始化器优于赋值语句
  • 条款13:使用静态构造器初始化静态类成员
  • 条款14:利用构造器链

Have Fun :)