bool vs void *在同一个对象上施放

时间:2017-07-26 08:58:54

标签: c++ c++11 casting

下面的代码在if语句中使用时会输出'operator bool',而在需要bool进行函数调用时会输出'operator void *'。

为什么不使用operator bool进行函数调用?以及如何在两种情况下都使用它?

#include <iostream>

class A
{
public:
    explicit operator bool() const
    {
        std::cout << "operator bool" << std::endl;
        return true;
    }

    operator void*() const
    {
        std::cout << "operator void*" << std::endl;
        return 0;
    }
};

void f(bool valid)
{
    std::cout << "f called " << valid << std::endl;
}

int main(int argc, char *argv[])
{
    A a;

    if(a)
        std::cout << "if a" << std::endl;

    f(a);

    return 0;
}

2 个答案:

答案 0 :(得分:21)

if语句中,考虑隐式和显式转换运算符。由于Aoperator bool,因此选择一个,因为它比将A转换为void*然后将其转换为bool更好。

但是在其他语句中,不是条件(ifwhile,...),显式转换运算符不参与重载解析,而唯一有效的运算符则是{ {1}},可以使用,因为存在从指针到operator void*的隐式转换。

如果您希望选择bool,则需要将其设为非operator bool,或使用强制转换(因为这是标记为explicit的含义,确保必须明确使用它):

explicit

答案 1 :(得分:5)

原因是使用函数说明符explicit声明了运算符。

在if语句的条件下,该值在上下文中转换为bool类型。

来自C ++标准(4次标准转换)

  

2 [注意:将隐式转换具有给定类型的表达式   在几种情况下的其他类型:

...

  

- 在if语句或迭代语句的条件中使用   (6.4,6.5)。目的地类型是bool。

但是当值作为参数传递给函数时,会使用所谓的复制初始化。在这种情况下,函数说明符explicit会阻止转换为bool类型。

来自C ++标准(12.3.2转换函数)

  

2 转换函数可能是显式的(7.1.2),在这种情况下它是   仅被视为用户定义的直接初始化转换   (8.5)。否则,用户定义的转换不限于使用   在作业和初始化中。

强制调用bool运算符的一种简单方法是以下

f( bool( a ) );