最近在coding的時(shí)候,寫了這么一段代碼:
A.h
1
// A.h
2
#include <map>
3
4
class A
5

{
6
public:
7
static std::map<int, int> x;
8
};
A.cpp
1
// A.cpp
2
#include "A.h"
3
4
std::map<int, int> Test::x;
很簡(jiǎn)單,也很正常,看看用法吧。
main.cpp
1
class B
2

{
3
public:
4
B();
5
};
6
7
class C
8

{
9
public:
10
static B b;
11
};
12
13
B C::b;
14
15
B::B()
16

{
17
A::x[1] = 2;
18
}
19
20
void main()
21

{
22
A::x[3] = 3;
23
}
好了,按照上面的寫法,把代碼分別放到3個(gè)文件里面,編譯,通過, 鏈接,通過,運(yùn)行,掛了!!why?
解決方案很簡(jiǎn)單,把A.cpp里面的那句定義放到main.cpp里面就好了。
問題在于兩個(gè)static變量分別在兩個(gè)不同的文件里,A.cpp 里面那static變量要在main.cpp前初始化才行,可是編譯器不知道呀,結(jié)果main里面的先初始化了,等到調(diào)用A.cpp里面那個(gè)變量時(shí),已經(jīng)來不及啦。
這個(gè)就是
依賴編譯器初始化順序的程序,如果有人運(yùn)行沒有掛,那恭喜啦,等到它掛的時(shí)候你可要哭了。
上面的解決方案太爛了,如果程序規(guī)模很大,就完了,比如有好幾個(gè)cpp里面要用到A.cpp里面那個(gè)變量,放哪個(gè)里面好呢?
這時(shí)候,Scott Mayer的Singleton就是解決方案啦,它能保證靜態(tài)變量在使用前被初始化。
看看下面的代碼:
1
class static_
2

{
3
public:
4
template <int N, class T>
5
static T& var()
6
{
7
static T instance;
8
return instance;
9
}
10
11
private:
12
~static_()
{}
13
};
有了這個(gè)定義,想用靜態(tài)變量的時(shí)候就爽啦~~,用的時(shí)候:
1
static_::var<0, std::string>() = ":)";
2
static_::var<0, std::map<int, int> >()[0] = 3;
3
static_::var<1, std::string>() = "haha";
現(xiàn)在的效果就是,想讓Test里面有什么,他就有什么,我指靜態(tài)變量。注意啦,第一個(gè)模板參數(shù)是為了可以定義同種類型的多個(gè)變量,就相當(dāng)于
var_0, var_1...
是不是感覺有點(diǎn)動(dòng)態(tài)語言的特性了,變量不用定義就可以用。而且變量初始化順序也不用關(guān)心啦,因?yàn)樗械淖兞繒?huì)在使用前初始化完畢。
如果和boost::function合作起來,效果更佳。look!
1
class Fun
2

{
3
public:
4
Fun()
5
: UId(&static_::var<0, std::string>)
6
{
7
}
8
// interface for static variable.
9
boost::function<std::string& (void)> UId;
10
};
11
12
void main()
13

{
14
Fun f1, f2;
15
// set static from f1
16
f1.UId() = "abc";
17
// get static from f2
18
std::string str = f2.UId();
19
}
好了,static就到這里吧。
posted on 2009-03-20 14:16
尹東斐 閱讀(4657)
評(píng)論(5) 編輯 收藏 引用