Last active
July 13, 2016 07:33
-
-
Save LusainKim/ff7ec985cb90e0d322ff0a50381441d8 to your computer and use it in GitHub Desktop.
enum class example
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#include <iostream> | |
namespace EnumFunc { | |
template<typename Enum> // Enum class의 선언형을 알려주어 인자와 대응하는 값을 반환하는 함수입니다. | |
inline constexpr auto GetEnumValueByType(Enum enumerator) noexcept // enum class E : int { a,b,c }; 일 때, | |
{ // auto data = GetEnumValueByType(E::a); | |
return static_cast<std::underlying_type_t<Enum>>(enumerator); // data의 형식은 int 이고, 값은 0 입니다. | |
} | |
// 다음 함수부터의 전제 조건 : 함수에서 사용 가능한 모든 열거형은 | |
// none = 0 으로 시작하여 count 로 끝나야 한다. | |
template<typename Enum> | |
inline Enum SetRandomEnum() noexcept | |
{ | |
using Ty = decltype(GetEnumValueByType(Enum::none)); | |
Ty randomInt{ (rand() % (GetCharType(Enum::count) - 1) + 1) }; | |
// 잠재적 버그구간 | |
return static_cast<Enum>(randomInt); | |
} | |
template<typename Enum> | |
inline Enum& operator++(Enum& c) | |
{ | |
auto ty = (GetEnumValueByType(c) + 1) % GetEnumValueByType(Enum::count); | |
c = static_cast<Enum>(ty | |
+ (ty == GetEnumValueByType(Enum::none) ? 1 : 0)); | |
return c; | |
} | |
template<typename Enum> | |
inline Enum operator++(Enum& c, int) | |
{ | |
Enum ret = c; | |
++c; | |
return ret; | |
} | |
template<typename Enum> | |
inline Enum operator+(Enum c, Enum o) | |
{ | |
auto lv = GetEnumValueByType(c); | |
auto rv = GetEnumValueByType(o); | |
auto ty = (lv + rv) % GetEnumValueByType(Enum::count); | |
return static_cast<Enum>(ty | |
+ (ty == GetEnumValueByType(Enum::none) ? 1 : 0) ); | |
} | |
}; | |
// ----------------------------------------------------------------------------------- | |
// 예제 | |
// ----------------------------------------------------------------------------------- | |
#include <string> | |
using namespace std; | |
enum class Character : char { | |
none | |
, 전사 | |
, 마법사 | |
, 성직자 | |
, 궁수 | |
, count | |
}; | |
inline constexpr auto GetCharType(Character e) noexcept { return EnumFunc::GetEnumValueByType(e); } | |
inline ostream& operator<<(ostream& Ostr, const Character f) noexcept | |
{ | |
string output; | |
switch (f) | |
{ | |
case Character::전사: output = string("전사"); break; | |
case Character::마법사: output = string("마법사"); break; | |
case Character::성직자: output = string("성직자"); break; | |
case Character::궁수: output = string("궁수"); break; | |
} | |
Ostr << output; | |
return Ostr; | |
} | |
int main() | |
{ | |
using namespace EnumFunc; | |
for (int i = 0; i < GetCharType(Character::count) * 2; ++i) | |
{ | |
Character lunit{ EnumFunc::SetRandomEnum<Character>() }; | |
Character runit{ EnumFunc::SetRandomEnum<Character>() }; | |
++lunit; | |
runit++; | |
cout << lunit << "(" << GetCharType(lunit) << ")"; | |
cout << " + "; | |
cout << runit << "(" << GetCharType(runit) << ")"; | |
cout << " = "; | |
Character retunit = lunit + runit; | |
cout << retunit << "(" << GetCharType(retunit) << ")" << endl; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
scoped enum 을 사용하는 예제입니다.