【一天一個C++小知識】001.C++中的static關鍵字

1. 面向過程設計的static

1.1. 靜態全局變量

  全局變量加上static稱爲靜態全局變量:

  • 靜態全局變量在全局數據區分配內存
  • 未經初始化的靜態變量會被程序自動初始化爲0
  • 靜態全局變量在聲明它的整個文件中都是可見的,文件之外不可見

1.2. 靜態局部變量

  局部變量加上static稱爲靜態局部變量。通常函數體內定義一個變量,每當程序運行到該語句時都會給局部變量分配棧內存,隨着程序退出函數體,系統就會回收棧內存,局部變量相應失效。

  但若需要兩次調用之間對變量的值進行保存,通常可以定義一個全局變量,但這樣變量不再屬於函數本身,不再僅受函數控制,程序維護不便。

  靜態局部變量的特點:

  • 該變量在全局數據區分配內存
  • 靜態局部變量在程序執行到該對象處時首次初始化,之後對函數的調用不再進行初始化過程
  • 靜態局部變量一般在聲明處初始化
  • 始終駐留在全局數據區,知道程序運行結束,但是其作用域爲局部作用域,當定義它的函數或語句塊結束時,其作用域隨着結束
  • 可以進行二次賦值操作

1.3. 靜態函數

  靜態函數就是函數前加static,靜態函數不能被其他文件所用,可以避免定義相同名字的函數使發生衝突.

2. 面向對象中的static

2.1 靜態數據成員

  對於非靜態數據成員,每個類對象都有自己的拷貝,而靜態數據成員被當作是類的成員,無論這個類的對象被定義了多少個,靜態數據成員在程序中只有一份拷貝,由該類型的所有對象共享訪問。也就是說,靜態數據成員是該類的所有對象所共有的,對該類的多個對象來說,靜態數據成員只分配一次內存,供所有對象公用。所以靜態數據成員的值對每個對象都是一樣的,它的值可以更新。

  靜態數據成員存儲在全局數據區,定義時分配空間,所以不能再類聲明中定義。

2.2. 靜態成員函數

  與靜態數據成員一樣,靜態成員函數爲類的全部對象服務而不是某一個類的具體對象。他們都屬於類定義的一部分。普通的成員函數一般都隱含了this指針,this指針指向類的對象本身,通常情況下,這個指針是缺省的。但是靜態成員函數不與任何對象相聯繫,所以不具有this指針。也就是說,靜態成員函數不能訪問屬於類對象的非靜態數據成員/成員函數,它只能調用靜態成員函數。

2.3. 其他

  靜態數據成員要在程序一開始運行時就必須存在,因爲函數在程序運行中被調用,所以靜態數據成員不能在任何函數內分配空間和初始化。

  這樣的它的空間分配有三個可能的地方,一是作爲類的外部接口的頭文件(那裏有類聲明);二是類定義的內部實現(那裏有類的成員函數定義);三是應用程序的main函數前的全局數據聲明和定義處。

  靜態數據成員要實際地分配空間,故不能在類的聲明中定義(類聲明知識聲明一個類的尺寸和規格並不進行實際的內存分配)。也不能在頭文件中類聲明的外部定義(會造成多個使用該類的源文件中對其重複定義)。static被引入以告知編譯器將變量存儲在程序的靜態存儲區而非棧上空間。

  此外:

  • 不能將靜態成員函數定義爲虛函數
  • 靜態數據成員是靜態存儲的必須初始化
  • 爲了防止父類的影響,可以在子類中定義一個與父類相同的靜態變量,以屏蔽其影響。靜態成員爲父類和子類共享,但重複定義了靜態成員不會引起錯誤,這是因爲編譯器採用了name-mangling用於生成唯一的標誌。

Name-mangling是指爲了在目標文件符號表中和連接過程中使用的名字通常和編譯目標文件的源程序中的名字不一樣,編譯器將目標源文件中的名字進行調整


歡迎掃描二維碼關注微信公衆號 深度學習與數學   [每天獲取免費的大數據、AI等相關的學習資源、經典和最新的深度學習相關的論文研讀,算法和其他互聯網技能的學習,概率論、線性代數等高等數學知識的回顧]
在這裏插入圖片描述

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章