Сообщение Re[25]: Как записать такое в современном C++? от 01.08.2024 13:18
Изменено 01.08.2024 14:16 kov_serg
Re[25]: Как записать такое в современном C++?
Здравствуйте, so5team, Вы писали:
S>В случае простых enum-ов оно не работает для типов, отличных от int.
S>В случае enum class оно не работает для типов, отличных от целочисленных, да еще и требует указывать дополнительный скоуп.
S>В общем, оно не работает. А я опять вляпался в известную субстанцию в попытках объяснить персонажам вроде вас очевидные вещи
Всё работает просто вы не так используете. В C++ принято всё через жопу делать
S>В случае простых enum-ов оно не работает для типов, отличных от int.
S>В случае enum class оно не работает для типов, отличных от целочисленных, да еще и требует указывать дополнительный скоуп.
S>В общем, оно не работает. А я опять вляпался в известную субстанцию в попытках объяснить персонажам вроде вас очевидные вещи
Всё работает просто вы не так используете. В C++ принято всё через жопу делать
#include <iostream>
using namespace std;
enum E {
name1,
name2,
name3
};
template<enum E e>const char* Es();
template<>const char* Es<name1>() { return "name1"; }
template<>const char* Es<name2>() { return "name2"; }
template<>const char* Es<name3>() { return "name3"; }
template<enum E e>double Ed();
template<>double Ed<name1>() { return 1; }
template<>double Ed<name2>() { return 0.5; }
template<>double Ed<name3>() { return 3.14; }
template<enum E e>bool Eс();
template<>bool Eс<name1>() { return true; }
template<>bool Eс<name2>() { return false; }
template<>bool Eс<name3>() { return false; }
static bool E_is_critical(enum E e) {
switch(e) {
case name1: return Eс<name1>();
case name2: return Eс<name2>();
case name3: return Eс<name3>();
}
throw;
}
template<enum E e>struct Eb;
template<>struct Eb<name1> {
template<class T>
static void run(T t) { t(); }
};
template<>struct Eb<name2> {
template<class T>
static void run(T t) { try { t(); } catch(...) {} }
};
template<>struct Eb<name3> {
template<class T>
static void run(T t) { try { t(); } catch(...) { cerr<<"ups\n"; } }
};
int main(int argc, char const *argv[]) {
cout<<(Es<name1>())<<" "<<(Ed<name3>())<<endl;
Eb<name3>::run([]{ throw 0; });
return E_is_critical(name2);
}Re[25]: Как записать такое в современном C++?
Здравствуйте, so5team, Вы писали:
S>В случае простых enum-ов оно не работает для типов, отличных от int.
S>В случае enum class оно не работает для типов, отличных от целочисленных, да еще и требует указывать дополнительный скоуп.
S>В общем, оно не работает. А я опять вляпался в известную субстанцию в попытках объяснить персонажам вроде вас очевидные вещи
Всё работает просто вы не так используете. В C++ принято всё через жопу делать
S>В случае простых enum-ов оно не работает для типов, отличных от int.
S>В случае enum class оно не работает для типов, отличных от целочисленных, да еще и требует указывать дополнительный скоуп.
S>В общем, оно не работает. А я опять вляпался в известную субстанцию в попытках объяснить персонажам вроде вас очевидные вещи
Всё работает просто вы не так используете. В C++ принято всё через жопу делать
#include <iostream>
using namespace std;
enum E {
name1,
name2,
name3
};
template <template<enum E> class M>
static auto E_get_value(enum E e) {
switch(e) {
case name1: return M<name1>::value();
case name2: return M<name2>::value();
case name3: return M<name3>::value();
}
throw;
}
template <template<enum E> class... M>
static auto E_forall(auto fn) {
fn(M<name1>::value()...);
fn(M<name2>::value()...);
fn(M<name3>::value()...);
}
template<enum E e>const char* Es();
template<>const char* Es<name1>() { return "name1"; }
template<>const char* Es<name2>() { return "name2"; }
template<>const char* Es<name3>() { return "name3"; }
template<enum E e>double Ed();
template<>double Ed<name1>() { return 1; }
template<>double Ed<name2>() { return 0.5; }
template<>double Ed<name3>() { return 3.14; }
template<enum E e>struct Ed_values;
template<>struct Ed_values<name1> { static double value() { return Ed<name1>(); }};
template<>struct Ed_values<name2> { static double value() { return Ed<name2>(); }};
template<>struct Ed_values<name3> { static double value() { return Ed<name3>(); }};
template<enum E e>struct Es_values;
template<>struct Es_values<name1> { static const char* value() { return Es<name1>(); }};
template<>struct Es_values<name2> { static const char* value() { return Es<name2>(); }};
template<>struct Es_values<name3> { static const char* value() { return Es<name3>(); }};
template<enum E e>struct Eb;
template<>struct Eb<name1> {
template<class T>
static void run(T t) { t(); }
};
template<>struct Eb<name2> {
template<class T>
static void run(T t) { try { t(); } catch(...) {} }
};
template<>struct Eb<name3> {
template<class T>
static void run(T t) { try { t(); } catch(...) { cerr<<"catch\n"; } }
};
int main(int argc, char const *argv[]) {
// не целые константы
cout<<(Es<name3>())<<"="<<(Ed<name3>())<<endl;
// получение значение
enum E e=name2; cout<<E_get_value<Ed_values>(e)<<endl;
// перебираем все значения
E_forall<Es_values,Ed_values>([](const char* name,double value){
cout<<name<<"="<<value<<endl;
});
// выбираем алгоритм по имени
Eb<name3>::run([]{ throw 0; });
return 0;
}name3=3.14
0.5
name1=1
name2=0.5
name3=3.14
catch