剛剛開始學習寫些c++程式,很多問題都不懂。在看大牛的程式的時候思路更不跟不上,很多東西都要慢慢的沉澱積累。為此,記下一些知識點,以便以後複習。
本文轉自:http://blog.csdn.net/adriano119/article/details/2991317
--------------------------------STATIC--------------------------------
對於一個完整的程式,記憶體中的分布情況:
==========
| 代碼區 |
------------------
| 全域資料區 |
------------------
| 堆區 |
-----------------
| 棧區 |
==========
一般程式的由new產生的動態資料存放在堆區,函數內部的自動變數存放在棧區,全域變數和static變數放在全域資料區
static的作用主要有以下3個:
1、擴充生存期;(面向過程:局部)
2、限制範圍;(面向過程:全域)
3、唯一性。(物件導向)
STATIC:
一、面向過程設計中的static
1、[靜態全域變數] //在全域變數前,加上關鍵字static,該變數就被定義成為一個靜態全域變數。
靜態全域變數有以下特點:
1)該變數在全域資料區分配記憶體;
2)未經初始化的靜態全域變數會被程式自動初始化為0(自動變數的值是隨機的,除非它被顯式初始化);
3)靜態全域變數在聲明它的整個檔案都是可見的,而在檔案之外(extern)是不可見的;
定義全域變數就可以實現變數在檔案中的共用,但定義靜態全域變數還有以下好處:
1)靜態全域變數不能被其它檔案所用;
2)其它檔案中可以定義相同名字的變數,不會發生衝突;
2、[靜態局部變數] 在局部變數前,加上關鍵字static,該變數就被定義成為一個靜態局部變數。
通常,在函數體內定義了一個變數,每當程式運行到該語句時都會給該局部變數分配棧記憶體。但隨著程式退出函數體,系統就會收回棧記憶體,局部變數也相應失效。但有時候我們需要在兩次調用之間對變數的值進行儲存。通常的想法是定義一個全域變數來實現。但這樣一來,變數已經不再屬於函數本身了,不再僅受函數的控制,給程式的維護帶來不便。
靜態局部變數正好可以解決這個問題。靜態局部變數儲存在全域資料區,而不是儲存在棧中,每次的值保持到下一次調用,直到下次賦新值。
靜態局部變數有以下特點:
1)該變數在全域資料區分配記憶體;
2)靜態局部變數在程式執行到該對象的聲明處時被首次初始化,即以後的函數調用不再進行初始化;
3)靜態局部變數一般在聲明處初始化,如果沒有顯式初始化,會被程式自動初始化為0;
4)它始終駐留在全域資料區,直到程式運行結束。但其範圍為局部範圍,當定義它的函數或語句塊結束時,其範圍隨之結束;
3、靜態函數
在函數的傳回型別前加上static關鍵字,函數即被定義為靜態函數。靜態函數與普通函數不同,它只能在聲明它的檔案當中可見,不能被其它檔案使用。
定義靜態函數的好處:
1)靜態函數不能被其它檔案所用;
2)其它檔案中可以定義相同名字的函數,不會發生衝突;
二、物件導向的static關鍵字(類中的static關鍵字)
1、待用資料成員
在類內資料成員的聲明前加上關鍵字static,該資料成員就是類內的待用資料成員。
待用資料成員有以下特點:
1)而待用資料成員被當作是類的成員。無論這個類的對象被定義了多少個,靜態數 據成員在程式中也只有一份拷貝,由該類型的所有對象共用訪問。
2)待用資料成員儲存在全域資料區,屬於本類的所有對象共用,所以,它不屬於特定的類對象,在沒有產生類對象時其範圍就可見,即在沒有產生類的執行個體時,我們就可以操作它;
同全域變數相比,使用待用資料成員有兩個優勢:
1)待用資料成員沒有進入程式的全域名字空間,因此不存在與程式中其它全域名字衝突的可能性;
2)可以實現[資訊隱藏]。待用資料成員可以是private成員,而全域變數不能;
2、靜態成員函數
它為類的全部服務而不是為某一個類的具體物件服務。與普通函數相比,靜態成員函數由於不是與任何的對象相聯絡(共用的,因此也是唯一的。沒有實體依靠,因此就沒有this指標,也沒必要有),因此它不具有this指標。從這個意義上講,它無法訪問屬於類對象的非待用資料成員,也無法訪問非靜態成員函數,它只能調用其餘的靜態成員函數。
關於靜態成員函數,可以總結為以下幾點:
1)出現在類體外的函數定義不能指定關鍵字static;(因為這時候就不當做inline函數處理,見前面《C++中的標頭檔》)
2)靜態成員之間可以相互訪問,包括靜態成員函數訪問待用資料成員和訪問靜態成員函數;
3)非靜態成員函數可以任意地訪問靜態成員函數和待用資料成員;
4)靜態成員函數不能訪問非靜態成員函數和非待用資料成員
-----------------------------------EXTERN----------------------------
EXTERN
1 基本解釋
extern可以置於變數或者函數前,以標示變數或者函數的定義在別的檔案中,提示編譯器遇到此變數和函數時在其他模組中尋找其定義。通過這種行為它告訴編譯器:該變數/函數的定義已經存在在某個地方了,讓編譯器到其他的模組去尋找它的定義。
另外,extern也可用來進行連結指定。
2. extern “C”
使用extern“C”主要是因為C++語言在編譯的時候為了實現多態,會將函數名和函數結合起來形成另外一種函數名(總之就是說編譯後的函數名與你之前自己聲明時的函數名會不一樣),而C語言中無多態的概念當然也就不會有這種奇異的名字變化問題。這是問題就出現了,當你要在C++中調用C函數時,由於名字的不同,所以它會找不到所調用的這個函數的定義,因而會出錯。
為瞭解決這一C與C++的矛盾衝突,就有了extern "C'。
這裡面有幾個例子。
http://developer.51cto.com/art/201104/256820.htm
附加幾個問題:
1:extern和#include的差別
首先,#include是整個包含,extern是針對個別的;其次:#include裡面要從新定義和申明,而extern是告訴已經定義和申明了;最後,extern不能包含static成員,而#include可以。
2:函數前面加extern,表明函數在外部檔案可見,即外部檔案可以直接調用。