重载决策中的const指针

时间:2010-01-23 00:40:02

标签: c++ standards

GCC将这两个函数声明视为等效:

void F(int* a) { }
void F(int* const a) { }
  

test.cpp:在函数'void F(int *)'中:

     

test.cpp:235:错误:重新定义'void F(int *)'

     

test.cpp:234:错误:'void F(int *)'先前在此定义

这是有道理的,因为在这种情况下调用者总是会忽略const ...它只会影响函数内部参数'a'的使用。

我想知道的是标准在哪里(如果有的话)说,为了重载解析的目的,丢弃用作函数参数的指针的限定符是特别好的。

(我真正的问题是我想弄清楚GCC在内部剥离这些毫无意义的限定符的地方,并且由于GCC的C ++前端充斥着引用该标准的注释,标准的相关部分可能会帮助我找到正确的位置。)

4 个答案:

答案 0 :(得分:4)

标准在8.3.5 / 3中说为了确定函数类型,任何直接限定参数类型的cv限定符都将被删除。即它字面上说是一个声明为

的函数
void foo(int *const a);

有函数类型void (int *)

一个迂腐的人可能会争辩说,这并不足以说明上述声明应该像这样的定义相匹配

void foo(int *a)
{
}

或它应该使具有双重声明的代码(如在您的示例中)格式错误,因为这些概念都没有在函数类型的标准中描述。

我的意思是,我们都知道这些const是出于所有外部目的而被忽略的,但到目前为止,我无法在标准中找到最终确切地说明这一点的措辞。也许我错过了什么。

实际上,在13.1 / 3中它有一个“注释”,表示具有等效参数声明的函数声明(如8.3.5中所定义)声明相同的函数。但它只是一个注释,它是非规范性的,这表明在标准的某个地方应该有一些关于同一问题的规范性文本。

答案 1 :(得分:3)

我认为它基本上是禁止的:

void foo(int a) {}
void foo(const int a) {}
非引用的

const不参与重载。

事实上你甚至可以宣布

void foo(int a);

以后再定义

void foo(const int a) {}

其中constness纯粹是调用者不关心的实现细节。

答案 2 :(得分:2)

它与:

相同
void foo(int);
void foo(const int);

与来电者相同。这是因为函数无论如何都会获得副本值,因此调用者不关心它是否被认为是const;它没有任何区别。

编译器忽略这些事情 不合法,但重载决议没有区别。 const适用于函数的实现。

如果编译器处理了非法的话:

void foo(int i)
{
    i = 5; // good
}

void foo(const int)
{
    i = 5; // lolwut?
}

同样,忽略const

答案 3 :(得分:1)

我相信这是相反的方式。任何指针,甚至是非对象,都可以被视为const:)。