STATIC_ASSERT
-
ich möchte sowas machen:
template<class T> class Foo { STATIC_ASSERT(false); }; template<> class Foo<int> { void foobar(); }; template<> class Foo<double> { int barfoo(); }; //und wenn einer schreibt Foo<double> f; //soll es funktionieren. //aber bei Foo<char> f; //soll es beim STATIC_ASSERT rausfliegen, weil ich kein Foo<char> angeboten //habe.
was mich wundert, ist daß bei Foo<double> f; auch das STATIC_ASSERT rausfliegt. dabei hab ich doch das allgemeine template gar nicht instanziiert, sondern nur das spezielle.
ist STATIC_ASSERT kaputt, war das ne design-enscheidung?
-
meinst du BOOST_STATIC_ASSERT?
Bei mir meldet der g++ einen Fehler (also ein assert)
> g++ -Wall -W -std=c++98 templspec.cc templspec.cc:10: Warnung: all member functions in class `Foo<int>' are private templspec.cc:15: Warnung: all member functions in class `Foo<double>' are private templspec.cc: In instantiation of `Foo<char>': templspec.cc:24: instantiated from here templspec.cc:6: error: invalid application of `sizeof' to an incomplete type
-
Hallo,
zumindest unter dem VC 6.0 funktioniert BOOST_STATIC_ASSERT hier nicht so wie erwünscht.Hier würde ich dir sowas vorschlagen:
template <class T> struct s_assert { template <bool b> struct In; template <> struct In<true> {}; }; #define STATIC_ASSERT(b) enum {a = sizeof(s_assert<T>::template In<b>)} template<class T> class Foo { STATIC_ASSERT(false); }; template<> class Foo<int> { void foobar(); }; template<> class Foo<double> { int barfoo(); }; Foo<double> ok; Foo<char> error;
Oder in Standard-C++:
template <class T, bool> class s_assert; template <class T> class s_assert<T, true> {}; #define STATIC_ASSERT(b) enum {a = sizeof(s_assert<T, b>)}
Wichtig ist auf jeden Fall, dass dein Test abhängig vom Templateparameter ist, da er ansonsten bereits im Basetemplate ausgeführt wird -> Fehler.
-
sorry. hab falsch geguckt.
ich dachte, er würde bei#include <boost/static_assert.hpp> template<class T> struct Foo { BOOST_STATIC_ASSERT(false); }; template<> struct Foo<int> { void foobar(); }; template<> struct Foo<double> { int barfoo(); }; int main(){ Foo<double> f; }
die assertion melden. ist aber nicht der fall. das ist gut.
-
...nur der VC 6 bekommt das natürlich wieder nicht auf die Reihe
-
HumeSikkins schrieb:
Wichtig ist auf jeden Fall, dass dein Test abhängig vom Templateparameter ist, da er ansonsten bereits im Basetemplate ausgeführt wird -> Fehler.
ja, diesen effekt hatte ich auch, als ich aus boost/static_array mit nur den code für die generic version rauskopiert hatte. (ich benutze MinGW studio).
ich habs aber so gelöst:#define STATIC_ASSERT(B) typedef char _staticAssert##__LINE__[2*bool(B)-1];
ist zwar doch nicht abhängig, aber klappt und ist erfreulich einfach.
-
HumeSikkins schrieb:
...nur der VC 6 bekommt das natürlich wieder nicht auf die Reihe
ich hab meinen vc6 jetzt in den ruhestand geschickt.
-
volkard schrieb:
HumeSikkins schrieb:
...nur der VC 6 bekommt das natürlich wieder nicht auf die Reihe
ich hab meinen vc6 jetzt in den ruhestand geschickt.
Ich warte damit noch bis ich mein Windows 98 in den Ruhestand schicke...
-
HumeSikkins schrieb:
Hallo,
zumindest unter dem VC 6.0 funktioniert BOOST_STATIC_ASSERT hier nicht so wie erwünscht.Hier würde ich dir sowas vorschlagen:
template <class T> struct s_assert { template <bool b> struct In; template <> struct In<true> {}; }; #define STATIC_ASSERT(b) enum {a = sizeof(s_assert<T>::template In<b>)} template<class T> class Foo { STATIC_ASSERT(false); }; template<> class Foo<int> { void foobar(); }; template<> class Foo<double> { int barfoo(); }; Foo<double> ok; Foo<char> error;
...
Hallo,
kannst du mir erklaeren, was genau hier passiert? Hab Probleme, dass genau
zu verstehen.mfg
v R
-
HumeSikkins schrieb:
Ich warte damit noch bis ich mein Windows 98 in den Ruhestand schicke...
das will ich sehen ....
-
#define STATIC_ASSERT(b) enum {a = sizeof(s_assert<T>::template In<b>)}
wenn b false ist funktioniert sizeof nicht, weil es von s_assert::In nur für true eine spezialisierung gibt und der rest nicht definiert ist.
HumeSikkins schrieb:
Oder in Standard C++
template <class T, bool> class s_assert; template <class T> class s_assert<T, true> {}; #define STATIC_ASSERT(b) enum {a = sizeof(s_assert<T, b>)}
Wichtig ist auf jeden Fall, dass dein Test abhängig vom Templateparameter ist, da er ansonsten bereits im Basetemplate ausgeführt wird -> Fehler.
-
davie schrieb:
#define STATIC_ASSERT(b) enum {a = sizeof(s_assert<T>::template In<b>)}
wenn b false ist funktioniert sizeof nicht, weil es von s_assert::In nur für true eine spezialisierung gibt und der rest nicht definiert ist.
HumeSikkins schrieb:
Oder in Standard C++
template <class T, bool> class s_assert; template <class T> class s_assert<T, true> {}; #define STATIC_ASSERT(b) enum {a = sizeof(s_assert<T, b>)}
Wichtig ist auf jeden Fall, dass dein Test abhängig vom Templateparameter ist, da er ansonsten bereits im Basetemplate ausgeführt wird -> Fehler.
Jetzt isses klar, danke!
mfg
v R