Mam następujący kod:dla typu szablonu argument nie jest stałym wyrażeniem
#include <cstdlib>
#include <cstdio>
#include <atomic>
enum ATYPE { Undefined = 0, typeA, typeB, typeC };
template<ATYPE TYPE = Undefined>
struct Object
{
Object() { counter++; }
static std::atomic<int> counter;
};
template<ATYPE TYPE>
std::atomic<int> Object<TYPE>::counter(1);
template<ATYPE TYPE>
void test()
{
printf("in test\n");
Object<TYPE> o;
}
int main(int argc, char **argv)
{
test<typeA>();
printf("%d\n", Object<typeA>::counter.load());
Object<typeA>::counter.store(0);
for (int i = 0; i < sizeof(ATYPE); ++i) {
Object<static_cast<ATYPE>(i)>::counter.store(0);
}
return 0;
}
Kiedy skompilować z poniższej linii poleceń:
clang++ -o test -std=c++11 -stdlib=libc++ test.cpp
otrzymuję następujące błędy:
test.cpp:32:20: error: non-type template argument is not a constant expression
Object<static_cast<ATYPE>(i)>::counter.store(0);
^~~~~~~~~~~~~~~~~~~~~
test.cpp:32:39: note: read of non-const variable 'i' is not allowed in a constant expression
Object<static_cast<ATYPE>(i)>::counter.store(0);
^
testray.cpp:31:18: note: declared here
for (int i = 0; i < sizeof(ATYPE); ++i) {
Rozumiem problem, w który wierzę. Argument szablonu musi być constexpr i wyraźnie nie jest. Pytanie brzmi, czy są możliwe zmiany, które mogę zrobić, aby to zadziałało. Przez to działa, to znaczy, czy mogę jakoś ma lepszego sposobu resetowania tych statycznych liczników z tej klasy szablonu dla każdego typu w Atype, inne niż po prostu robi to ręcznie:
Object<Undefined>::counter.store(0);
Object<typeA>::counter.store(0);
...
co nie jest tak elegancki i praktyczny gdy ATYPE zawiera wiele typów.
Bardzo dziękuję za pomoc i porady.
Tak czy inaczej, przeplatasz swoje wyliczenie. 'i' nie jest stałym wyrażeniem, tak jak pokazuje błąd. – Rapptz
@Rapptz, czy mógłbyś bardziej szczegółowo opisać swój pierwszy komentarz (niepoprawne wyliczenie enum). Wiem, że nie jestem const, więc dlatego pytam, czy jest jakiś sposób na zrobienie tego dzieła. Czy istnieje sposób na zapętlenie wszystkich elementów wyliczenia i zresetowanie liczników? Dziękuję Ci. – user18490
Co oznacza, że Rapptz jest dynamiczny i nie może być użyty jako szablon szablonu czasu kompilacji –