2013-12-08 82 views
21

我注意到,非靜態類可以有靜態構造函數:非靜態類中靜態構造函數的功能是什麼?

public class Thing 
{ 
    public Thing() 
    { 
     Console.WriteLine("non-static"); 
    } 

    static Thing() 
    { 
     Console.WriteLine("static"); 
    } 
} 

而當你初始化的Thing實例的靜態構造函數被首次調用。

輸出:

靜態

非靜態

會是什麼這方面的需要?你用它來初始化你的非靜態類型實例的靜態字段嗎?

使用靜態構造函數時是否有任何事項需要考慮?

+4

你自己回答'初始化靜態字段'。閱讀更多靜態構造函數[這裏](http://msdn.microsoft.com/en-us/library/k9x6w0hc.aspx)。 –

回答

23

您是否使用它來初始化您的非靜態類型實例的靜態字段?

非常多,除了靜態字段(或任何類型的靜態成員)不與實例相關聯;它們與類型本身相關聯,無論它是靜態類還是非靜態類。

documentation列表靜態構造的一些性質,其中之一是:

  • 靜態構造被自動調用創建或任何靜態成員引用的第一個實例之前初始化該類。

在這裏,「之前」的意思是「之前」,並且這些事情中的哪一個首先發生。這是因爲一個靜態構造函數在單個程序執行中僅被調用一次。


有什麼東西使用靜態構造函數時考慮到?

這裏是由上面的鏈接中給出的完整列表,這應該給你的使用靜態構造函數時所期待的想法:

  • 靜態構造函數並不需要訪問修飾符或有參數。

  • 在創建第一個實例或引用任何靜態成員之前,會自動調用靜態構造函數以初始化該類。

  • 無法直接調用靜態構造函數。

  • 用戶無法控制何時在程序中執行靜態構造函數。

  • 靜態構造函數的典型用法是當類使用日誌文件並使用構造函數將條目寫入此文件時。

  • 當構造函數可以調用LoadLibrary方法時,爲非託管代碼創建包裝類時,靜態構造函數也很有用。

  • 如果靜態構造函數拋出異常,則運行時不會再次調用該類型,並且該類型在運行程序的應用程序域的生存期內保持未初始化狀態。

除了確保你不要試圖訪問非靜態成員,因爲你在一個實例構造不是,你必須要考慮其他主要的是一個靜態構造函數總是被調用在程序執行期間的特定時間。如前所述,除了通過控制何時創建「第一個實例或引用任何靜態成員」之外,您無法控制此操作。

1

你用它來初始化或調用你的類的靜態成員。

1

這是個人經驗的主觀答案,但您也可以使用它來確保您班級以外的其他靜態變量的初始化,這些變量可能取決於您的班級的成員。

3

從MSDN Link

靜態構造函數被調用 一審之前自動初始化類 創建 或任何靜態成員被引用。

正如您所述,它用於初始化靜態字段。你只需要考慮一件事情,非靜態字段不會被初始化,直到你創建類的實例。

0

如上所述BoltClock's獨角獸上面。

但是一個很好的補充是,你可以用它來實現一個Singleton不錯,輕鬆地過:

public sealed class Singleton 
{ 
    private static readonly Singleton instance; 

    private Singleton() { } 

    static Singleton() 
    { 
     instance = new Singleton() 
    } 

    public static Singleton Instance 
    { 
     get 
     { 
     return instance; 
     } 
    } 
} 

更多細節可以在http://www.codeproject.com/Articles/90896/Singletons-in-C-Static-Constructor-vs-Static-Initi

+0

這不是使用靜態構造函數... – Servy

+0

被編輯爲包含正確的代碼和鏈接。道歉。 –

+0

但是沒有理由在這裏使用靜態構造函數;你之前的代碼通常比這更好,這使得使用靜態構造函數成爲一個糟糕的理由。 – Servy

1
  • 靜態構造函數被發現之前先自動調用該類的實例是 創建的。
  • 通過在構造函數定義中加上靜態關鍵字前綴聲明。
  • 它不能訪問修飾符或有任何參數。