@see online demo cpp.sh/2kiuy
@see inspiring blog post
@output
Has read permission
Has execute permission
@see online demo cpp.sh/2kiuy
@see inspiring blog post
@output
Has read permission
Has execute permission
// Example program | |
#include <iostream> | |
#include <string> | |
template<typename Enum> | |
struct EnableBitMaskOperators | |
{ | |
static const bool enable = false; | |
}; | |
#define ENABLE_BITMASK_OPERATORS(x) \ | |
template<> \ | |
struct EnableBitMaskOperators<x> \ | |
{ \ | |
static const bool enable = true; \ | |
}; | |
template<typename Enum> | |
typename std::enable_if<EnableBitMaskOperators<Enum>::enable, Enum>::type | |
operator &(Enum lhs, Enum rhs) | |
{ | |
using underlying = typename std::underlying_type<Enum>::type; | |
return static_cast<Enum> ( | |
static_cast<underlying>(lhs) & | |
static_cast<underlying>(rhs) | |
); | |
} | |
template<typename Enum> | |
typename std::enable_if<EnableBitMaskOperators<Enum>::enable, Enum>::type | |
operator ^(Enum lhs, Enum rhs) | |
{ | |
using underlying = typename std::underlying_type<Enum>::type; | |
return static_cast<Enum> ( | |
static_cast<underlying>(lhs) ^ | |
static_cast<underlying>(rhs) | |
); | |
} | |
template<typename Enum> | |
typename std::enable_if<EnableBitMaskOperators<Enum>::enable, Enum>::type | |
operator ~(Enum rhs) | |
{ | |
using underlying = typename std::underlying_type<Enum>::type; | |
return static_cast<Enum> ( | |
~static_cast<underlying>(rhs) | |
); | |
} | |
template<typename Enum> | |
typename std::enable_if<EnableBitMaskOperators<Enum>::enable, Enum>::type | |
operator |(Enum lhs, Enum rhs) | |
{ | |
using underlying = typename std::underlying_type<Enum>::type; | |
return static_cast<Enum> ( | |
static_cast<underlying>(lhs) | | |
static_cast<underlying>(rhs) | |
); | |
} | |
template<typename Enum> | |
typename std::enable_if<EnableBitMaskOperators<Enum>::enable, Enum>::type& | |
operator &=(Enum& lhs, Enum rhs) | |
{ | |
using underlying = typename std::underlying_type<Enum>::type; | |
lhs = static_cast<Enum> ( | |
static_cast<underlying>(lhs) & | |
static_cast<underlying>(rhs) | |
); | |
return lhs; | |
} | |
template<typename Enum> | |
typename std::enable_if<EnableBitMaskOperators<Enum>::enable, Enum>::type& | |
operator ^=(Enum& lhs, Enum rhs) | |
{ | |
using underlying = typename std::underlying_type<Enum>::type; | |
lhs = static_cast<Enum> ( | |
static_cast<underlying>(lhs) ^ | |
static_cast<underlying>(rhs) | |
); | |
return lhs; | |
} | |
template<typename Enum> | |
typename std::enable_if<EnableBitMaskOperators<Enum>::enable, Enum&>::type | |
operator |=(Enum& lhs, Enum rhs) | |
{ | |
using underlying = typename std::underlying_type<Enum>::type; | |
lhs = static_cast<Enum> ( | |
static_cast<underlying>(lhs) | | |
static_cast<underlying>(rhs) | |
); | |
return lhs; | |
} | |
enum class Permissions | |
{ | |
Readable = 0x4, | |
Writable = 0x2, | |
Executable = 0x1 | |
}; | |
ENABLE_BITMASK_OPERATORS(Permissions) | |
int main() | |
{ | |
Permissions p = Permissions::Readable | Permissions::Writable; // Set default permissions | |
p |= Permissions::Executable; // Add permission | |
p &= ~Permissions::Writable; // Remove permission | |
bool hasReadPermission = static_cast<bool>(p & Permissions::Readable); | |
bool hasWritePermission = static_cast<bool>(p & Permissions::Writable); | |
bool hasExecutePermission = static_cast<bool>(p & Permissions::Executable); | |
if (hasReadPermission) { | |
std::cout << "Has read permission" << "\n"; | |
} | |
if (hasWritePermission) { | |
std::cout << "Has write permission" << "\n"; | |
} | |
if (hasExecutePermission) { | |
std::cout << "Has execute permission" << "\n"; | |
} | |
} |