Static:靜態存儲,內部鏈接。
1.函數內部的靜態變量內部類型:在定義的時候初始化,如果未初始化,編譯器將其設置為0.
自定義類型:在定義的時候調用構造函數,如未傳遞參數,調用默認構造函數。包含局部對象的函數如果未被調用,則該局部對象不會構造,也不會析構。
void f()
{
static Obj b('b');
}
void g()
{
Obj c('c');
}
int main()
{
return 0;
}// no constructor both c and b
內部鏈接的好處是,可以將這個名字放在頭文件中而不用擔心鏈接時發生沖突。(鏈接時發現多個同一名字的定義會報錯,不知道該鏈接哪一個了)。通常將變量、內聯函數放在頭文件中,因為這些默認是內聯的。
鏈接只引用那些在鏈接/裝載期間有地址的成員,因此類聲明和局部變量并不鏈接。
2.全局變量:
static int a = 0;//definition, internal linkage, static storage area
extern int b = 0;//definition,external linkage, static storage area
3。局部變量:static只改變變量的存儲類型。而extern只是用作聲明,表示某處已經存在一個存儲區。
4。函數名:只改變可見性,static 僅該翻譯單元可見,extern(默認)外部可見。
名字空間解決沖突
1)只能在全局范圍內定義,可以相互嵌套
2)定義結尾處不需要有分號
3)可以在多個頭文件中用一個標識符
4)可以用另一個名字空間做別名
namespace longName
{
int i = 0;
}
namespace LN = longName;
5)不能創建實例
每個翻譯單元只能有一個未命名的名字空間,默認為內部鏈接。
namespace{
class A{};
class B{};
int i, j , k;
}
可以在一個名字空間的類定義之內插入一個友元聲明,該友元自動成為該名字空間的一員。
namespace Me
{
class Us{
friend void you();// you is member of namespace Me
};
}
使用名字空間
using 聲明
namespace U
{
inline void f(){}
inline void g(){}
}
namespae V
{
inline void f(){}
inline void g(){}
inline void g(int){}
inline char g(char){return 'a';}
}
void h()
{
using namespace U;
using V::g;//沒有類型方面的信息,聲明了這個空間中的所有重載函數
g();
g(1);
g('b');
U::g();
}
不要在頭文件中使用using namespace ...會污染所有包含該頭文件的編譯單元。
C++中的靜態成員
所有的類公用一塊內存區域,可以進行類內部通信。如果一個靜態數據成員被聲明但是未被定義,連接器會報一個錯誤。
定義必須出現在類的外部,且只能定義一次,通常放在類的實現文件中。
//.h file
class A
{
static int i ;
public:
//
};
//.cpp file
int A::i = 1;
這些都是類創建者應該做的,所以,客戶程序員不需要再定義一次了。
靜態數組的初始化
在類外初始化
class Value{
static const int scSize = 100;//非常特殊,內部類型可以這樣定義,也可以在類外定義。
static const float scFloat;
static const int scInts[];
};
const int Value::scFloat = 1.0f;
const int Value::scInts[]={2,23,4};
自定義類型: 必須在類外初始化
class Stat
{
static X x1;
static X xTable[];
static const X x2;
static const X xTable2[];
};
X Stat::x1(100);
X Stat::xTable[] = { X(1), X(2), X(3)};
const X Stat::x2(200);
const X Stat::xTable2 = {X(2), X(4), X(10) };
局部類中不能有static 數據成員。
靜態成員函數:沒有隱含的this指針,所以不能調用非靜態成員函數。
靜態初始化的相依性:一個對象的初始化必須需要另一個對象先初始化,如果初始化順序不對,則造成錯誤。解決方法:利用函數
1.頭文件中聲明一個函數,且不能為內聯。
2.實現文件中定義一個靜態對象,并返回引用。
//Dependency1StatFunc.h
#include "Dependency1.h"
extern Dependency1& d1();
//Dependency2StatFunc.h
#include "Dependency2.h"
extern Dependency2& d2();
//Dependency1StatFunc.cpp
#include "Denpendency1StatFunc.h"
Dependency1& d1()
{
static Deppendency1 dep1;
return dep1;
}
//Dependency2StatFunc.cpp 靜態對象一般放在單獨的文件中定義,但要在頭文件中聲明。
#include "Denpendency1StatFunc.h"
#include "Denpendency2StatFunc.h"
Dependency2& d2()
{
static Deppendency2 dep2(d1());//調用d1()的時候dep1已經初始化了
return dep2;
}
使用c類型的函數
extern "c" float f(int a);
extern "c"{
#include "Myheader.h"
}
extern "c"
{
float f();
double d();
}
posted on 2012-05-31 14:30
Dino-Tech 閱讀(137)
評論(0) 編輯 收藏 引用