重载static_cast?

Rad*_*dix 11 c++ casting

所以,我前几天参加了考试,其中一个问题与此类似:

我们有一个叫做Square变量的类int side.我们怎样才能cout << static_cast<int>(aSquare) <<endl;打印出a方形区域?

这甚至可能吗?

In *_*ico 23

有可能做到这一点,但不是通过重载static_cast<>().您可以通过重载类型转换运算符来实现:

class Square
{
public:
    Square(int side) : side(side) {}
    operator int() const { return side * side; } // overloaded typecast operator
private:
    int side;
};

// ...

// Compiler calls Square::operator int() to convert aSquare into an int
cout << static_cast<int>(aSquare) <<endl;
Run Code Online (Sandbox Code Playgroud)

请注意,过度使用类型转换操作符往往会带来更多弊大于利.他们可以进行大量无意义的隐式转换操作.当您阅读下面的这段代码片段时,您是否认为"a将会获得s的区域"?

Square aSquare;
int a = aSquare; // What the heck does this do?
Run Code Online (Sandbox Code Playgroud)

我当然不会.这使得更有意义并且更具可读性:

Square aSquare;
int a = aSquare.GetArea();
Run Code Online (Sandbox Code Playgroud)

更何况,通常你希望能够访问有关的其他信息Square,如GetSide()GetApothem()GetPerimeter()或什么的.operator int()显然只能返回一个int,并且你不能将多个operator int()s作为一个类的成员.

这是另一种情况,其中operator int()编译的代码仍无任何意义:

Square s;
if(s > 42) {} // Huh?!
Run Code Online (Sandbox Code Playgroud)

a Square大于42 是什么意思?这是无稽之谈,但是operator int()上面的代码将编译为Shape现在可以转换为int可以int与具有值的另一个进行比较的代码4.

所以不要写那样的类型转换操作符.事实上,如果你超载了类型转换操作符,你可能需要三思而后行.实际上只有少数情况下,在现代C++中重载类型转换操作符是有用的(例如安全的bool习语).

  • @In silico:使用c ++ 11,不再需要安全的bool习语,因为c ++ 11支持转换运算符的关键字`explicit`. (2认同)

Pub*_*bby 5

您可以重载强制转换运算符:

struct square {
  operator int() const {
    return (side * side);
  }
  int side;
};
Run Code Online (Sandbox Code Playgroud)

唯一的问题是它会被隐式使用,并且在这里转换没有多大意义。您也无法区分不同类型的强制转换(static_cast、c-style 等)

这是做事的首选方式:

struct square {
  int get_area() const {
    return (side * side);
  }
  int side;
}
Run Code Online (Sandbox Code Playgroud)

如果必须使用强制转换,请使用 C++11 功能并将其标记为explicit。这可以防止隐式转换错误。