2014-02-14 16 views
0

如果我有這樣的代碼:如何在編譯時將整數模板參數修改爲非零?

template<int SIZE = 0> 
class A { 
public: 

    union { 
     int buf[MagicThing]; 
     /* ... */ 
    }; 
}; 

在C++做一些(?宏)可以稱爲MagicThing其工作原理是這樣的:

  • 如果size> 0,則MagicThing == SIZE
  • if SIZE == 0 then MagicThing == 1

在編譯時? (Idealy不使用Boost庫等的需求,一些短伎倆)

回答

4

您可以使用:

int buf[SIZE > 0 ? SIZE : 1]; 
+0

哦,我很笨:-),謝謝! – user3123061

+0

如果SIZE <0,該怎麼辦?條件是「如果SIZE> 0,那麼MagicThing = SIZE,如果SIZE = 0 MagicThing = 1」 –

+2

未指定,因此實現特定:-)(在我的情況下爲1)。 – Jarod42

4

你可以試試這個

int buf[SIZE == 0 ? 1 : SIZE] 

,並SIZE未簽名,或添加static_assert檢查大小是否定的。當SIZE小於0時,您沒有指定想要的行爲。想必不會發生這種情況。

+0

無符號通常是一個壞主意,因爲標準要求將負值默默地轉化爲巨大的正值,這很少是一個好計劃。 – Yakk

+0

@Yakk我同意,純粹的'static_assert'可能是一個不錯的選擇。另一方面,對於大小使用'std :: size_t'是常規的。所以可以使用無符號整數*和* static_assert來檢查大小是否小於某個最大值。 – juanchopanza

1

(如果大小將始終爲0以上,其類型更改爲無符號的。)

一個瘋狂樣品溶液,這或許可以用作想法的其他情形(使用C++ 11資源):

#include <iostream> 

/* General case */ 
template<unsigned SIZE> 
constexpr unsigned MagicThing() 
{ 
    return SIZE; 
} 

/* Partial specialization when SIZE == 0 */ 
template<> 
constexpr unsigned MagicThing<0>() 
{ 
    return 1; 
} 

template<unsigned SIZE = 0> 
class A { 
public: 
    int buf[MagicThing<SIZE>()]; 

    size_t size() const 
    { 
     return sizeof(buf)/sizeof(int); 
    } 
}; 

int main() 
{ 
    A<0> a0; 
    A<1> a1; 
    A<5> a5; 

    std::cout << a0.size() << " " << a1.size() << " " << a5.size() << std::endl; 
} 

/* Compilation and execution */ 
$ gcc -std=c++11 sample.cpp 
$ ./a.out 
1 1 5 

其他(不是簡單的一個)的可能性是,使用新的static_if指示,提出了以下標準C++ 14,下一個(我不知道如果我的語法是正確的):

template<unsigned SIZE = 0> 
class A { 
public: 
    static_if (SIZE > 0) 
    int buf[SIZE]; 
    else 
    int buf[1]; 

    size_t size() const 
    { 
     return sizeof(buf)/sizeof(int); 
    } 
}; 
相關問題