本文共 2040 字,大约阅读时间需要 6 分钟。
最近在看pprint的源码,其中有段void类型强转的用法觉得见过,具体作用又记不起了,所以google了一下,记一下搜索的结果,以做备忘。源码如下:
templatevoid print_tuple(std::basic_ostream & os, Tuple const& t, seq ) { using swallow = int[]; // 这里做数组定义及初始化,初始化表第2项为逗号表达式,并做void的类型强转 (void)swallow{0, (void(os << (Is == 0? "" : ", ") << to_string(std::get (t))), 0)...}; }
偷个懒贴下检索结果好了,有时间了再梳理验证一下。
The comma operator, operator,. Unlike the built-in version, the overloads do not sequence their left operand before the right one. (until C++17) Because this operator may be overloaded, generic libraries use expressions such as a,void(),b instead of a,b to sequence execution of expressions of user-defined types. The boost library uses operator, in boost.assign, boost.spirit, and other libraries.
The relevant clause for this is 13.3.1.2/9 [over.match.oper] in N4140:
If the operator is the operator , the unary operator &, or the operator ->, and there are no viable functions, then the operator is assumed to be the built-in operator and interpreted according to Clause 5. Asvoid()
is never a valid function argument (see 5.2.2/7 [expr.call]), there never is a viable function and thus the built-in , will be used. So no, what you are trying to do is not possible. In fact, writing an iterator loop like this for(...; ++it1, (void)++it2)
is a standard way to prevent users from breaking your code by overloading , for their iterator types by enforcing the built-in operator , to be used. (Note that I am not saying you need to do this in your everyday code. It very much depends on its actual use. This is standard library level of paranoid.) The meaning of the operators =, (unary) &, and , (comma), predefined for each type, can be changed for specific class and enumeration types by defining operator functions that implement these operators. But such a function cannot be defined because, as I said above, void() is never a valid function argument. Now whether or not this is an oversight/problem in the standard is open to debate. 转载地址:http://fpcws.baihongyu.com/