函数签名忽略顶层const属性
字数统计:474
今天看《C++程序设计语言》12.1.3函数定义部分的时候注意到:void f(int) 和 void f(const int) 这两个声明对应一个函数,虽然这可能看起来违反“普遍”规则。Bjarne对此解释为为了兼容C。
实际上抛开兼容C,从语言本身来讲,将这两种函数声明视为一种是行得通的,因为顶层cv限定只影响对应函数实现部分的语义,换句话说顶层 const 为参数时,调用者不必关心该限定,完全是函数内部实现负责的约束,因此可以视为同一签名。
这个规则只影响顶层cv限定的情况,不影响引用或者指针:
class foo {
int f1{};
};
foo a(const foo a1, const foo b1)
{
std::cout << "const" << std::endl;
return a1;
}
foo a(foo a1, const foo b1) // 重复定义
{
std::cout << "non-const" << std::endl;
/* */
return a1;
}
int main() {
foo d, e;
const foo h;
foo f = a(h, e);
foo g = a(d, e);
}
注意,在a的函数调用过程中一定发生了对对象的复制,此时规则才成立。
对于非顶层 const,则不遵循此规则,因为非顶层 const 的调用过程并没有复制对象:
class foo {
int f1{};
};
foo a(const foo* a1, const foo* b1)
{
std::cout << "const" << std::endl;
return *a1;
}
foo a(foo* a1, const foo* b1) // a发生了重载
{
std::cout << "non-const" << std::endl;
/* */
return *a1;
}
int main() {
foo d, e;
foo f = a(const_cast<const foo*>(&d), &e);
foo g = a(&d, &e);
}
由于上述两个 a 的重载都没有涉及顶层 const,所以并不是重定义。
涉及顶层 const 的写法如下:
foo a(const foo* a, const foo* b);
foo a(const foo* a, const foo* const b); // 与上一行是同一函数声明
若无特殊声明,本人原创文章以
CC BY-SA 4.0许可协议
提供。
本站不欢迎非搜索引擎类,非个人学习类爬虫;严禁将文章直接爬取至其他站点。
若看到此条消息,说明你正在访问的网站可能是垃圾二手转载网站。
为了获得更好的浏览体验,请访问唯一原始网站:mysteriouspreserve[dot]com或blog[dot]bizwen[dot]com。