在C++中,有什么最好的方式来创建一个包含三个值的布尔变量呢?
我希望我的数组中的字段可以设置为true
、false
或者不设置。
如果我这样声明它们:
t[0] = true;
t[1] = false;
t[2] = NULL;
当我测试条件时,我得到了以下结果:
t[2]
是false
。在C++中,有什么最好的方式来创建一个包含三个值的布尔变量呢?
我希望我的数组中的字段可以设置为true
、false
或者不设置。
如果我这样声明它们:
t[0] = true;
t[1] = false;
t[2] = NULL;
t[2]
是false
。这应该可以正常工作:
t[0] = true;
t[1] = false;
t[2] = -1;
如果您只需要3种状态,但可能在某些时候需要更多,那么 enum
很棒:
enum STATES
{
NULL_STATE = -1, // you can manually specify -1 to give it a special case value
FALSE, // will be equal to 0
TRUE // will be equal to 1
};
0/false
返回 false
。-1和true都返回true。您可能想使用以下switch来处理三个或更多状态:switch (var) // may need to cast: (int)var
{
case 1:
case 0:
case -1:
};
如果你希望使用if语句块,也可以采用如下方式:
if (var == -1) // or (var == NULL_STATE)
{}
else if (var) // true condition
{}
else // false
{}
std :: experimental :: optional <bool>(如果您的C ++标准库具有它),或boost :: optional <bool>(www.boost.org)。
我认为std :: optional 是C ++ 17的候选项,因此如果您采用上述方法,则到C ++ 17的重构工作应该是最小的。
如果您不喜欢使用尚未在“正确”的C ++标准库中的内容,则考虑:
1. 基于 std :: unique_ptr<bool>的某些内容
2. std :: pair<bool, bool>
3. 具有3个值的传统 enum 。
std::optional
来实现此功能:std::optional<bool> t[3];
t[0] = true;
t[1] = false;
t[2] = std::nullopt;
for (auto const& i : t)
if (i.has_value()) std::cout << i.value() << '\n';
输出:
1
0
boost::optional<bool> myBooleanVariable;
enum class tristate{true,false,undefined=0};
它们简单易用,易于理解,并提供对纯旧枚举的类型安全。由于它们是类型安全的,因此您无法意外地将其与不同类型的枚举或数字类型进行比较,但这也意味着您无法使用位操作和整数技巧。除非指定了不同的类型,否则枚举类是一个初始化为“0”的数字类型。这意味着通过将值“0”分配给其中一个枚举值,您可以使其成为默认状态。
tristatet[7];
t[1] = tristate::true;
t[2] = tristate::false;
t[3] = tristate::undefined;
t[4] = false; //error
t[5] = 0; //error
t[6] = null; //error
t[0] == true; //error
t[0] == tristate::true; // false
t[0] == tristate::undefined; // true
switch(t[2]) {
case tristate::true:
foo(); break;
case tristate::false:
bar(); break; //t[2] was set to tristate::false
case tristate::undefined :
doNothing(); break;
}
我认为枚举声明是更加干净和简单的解决方案。
关于新类型大小的一点说明:枚举类型通常(当然取决于编译器)由整数支持,因此您将分配大约32或64位来实际使用2位。
在较新的C ++(C ++ 11)中,您可以指定枚举的基础类型(为现有的整数类型)。例如:
enum tribool: uint8_t {False = 0, True = 1, Unknown = 2};
...
enum tribool f = tribool::False;