可變引數模板(Variadic Templates)
要解決的問題:
- 怎麼建立一個擁有1個、2個或者更多的初始化器的類?
- 怎麼避免建立一個例項而只拷貝部分的結果?
- 怎麼建立一個元組?
最後的問題是關鍵所在:考慮一下元組!如果你能建立並且訪問一般的元組,那麼剩下的問題也將迎刃而解。
這裡有一個例子(摘自“可變引數模板簡述(A brief introduction to Variadic templates)”(參見參考)),要構建一個廣義的、型別安全的printf()。這個方法比用boost::format好的多,但是考慮一下:
1 2 3 4 |
const
string pi = “pi”; const
char *
m =
“The
value of %s is about %g (unless you live in %s).n”;
printf (m,
pi, 3.14159, “Indiana”);
|
這是除了格式字串之外,沒有其它引數的情況下呼叫printf()的一個最簡單的例子了,所以我們將要首先解決:
1 2 3 4 5 6 7 8 9 |
void
printf ( const
char *
s) {
while
(s && *s) {
if
(*s==’%’ && *++s!=’%') //保證沒有更多的引數了
//%%(轉義字元,在格式字串中代表%
throw
runtime_error(“格式非法: 缺少引數”);
std::cout
<< *s++<<endl;
}
}
|
這個處理好之後,我們必須處理有更多引數的printf():
1 2 3 4 5 6 7 8 9 10 11 12 13 |
template < typename
T, typename ...
Args> //
注意這裡的"..."
void
printf ( const
char *
s, T value, Args... args) //
注意"..."
{
while
(s && *s) {
//一個格式標記(避免格式控制符)
if
|