c++ - 具有默认参数的 C++ 函数的多个声明

标签 c++ c++11

我对几乎所有东西都使用 typedef,包括函数。在过去的几周里,我一直在使用最终草案文档 (N3242) 作为指南来优化我们的 C++ 代码以尽可能完全符合 ISO C++11 标准。

正如我们所知,偶尔会有多个声明通过出现在多个文件中的 extern 或重复的 typedef 潜入我们的代码中。根据上述 doco 第 145 页第 7.1.3 节的摘录,这应该是无害的:

3. In a given non-class scope, a typedef specifier can be used to redefine the name of any type declared in that scope to refer to the type to which it already refers.

[ Example:

   typedef struct s { /* ... */ } s; 
   typedef int I; 
   typedef int I; 
   typedef I I;

— end example ]

所以,我写了一个程序来测试这个。最简单的形式:

typedef int (fcntype)(int, int);
extern fcntype fcn1;

int fcn1(int x, int y) { return x + y; }

int main(int argc, char ** argv) { return fcn1(2, 3); }

使用gcc编译

 -Wfatal-errors -Wswitch-default -Wswitch-enum -Wunused-parameter -Wfloat-equal -Wundef -c -Wstrict-null-sentinel -std=c++0x -pedantic -Wall -Wextra

当然没有问题。让我们复制函数声明:

typedef int (fcntype)(int, int);
extern fcntype fcn1;
extern fcntype fcn1; // woops. probably from an #include ...

int fcn1(int x, int y) { return x + y; }

int main(int argc, char ** argv) { return fcn1(2, 3); }

正如标准预测的那样,没有问题。让我们对原始文件进行不同的更改:

typedef int (fcntype)(int, int=0); // default param.
extern fcntype fcn1;

int fcn1(int x, int y) { return x + y; }

int main(int argc, char ** argv) { return fcn1(2); } // use the default param

同样,没问题。当我们同时拥有重复的 decl 和默认参数时,问题就出现了:

typedef int (fcntype)(int, int=0); // default param.
extern fcntype fcn1;
extern fcntype fcn1; // FYI this is line 3 in the error message below.

int fcn1(int x, int y) { return x + y; }

int main(int argc, char ** argv) { return fcn1(2); } // use the default param

gcc 提示

decltest.cpp:3: error: default argument given for parameter 2 of ‘int fcn1(int, int)’

当然,我正在按照应该清理的方式清理代码,也就是说我正在将 decl 合并到一个组织得更好的文件中。但这是编译器中的错误还是我对默认参数“是什么”的误解?

最佳答案

首先,对于具有相同类型的相同函数声明,最多只能有一个定义默认参数的声明。这是由于 §8.3.6 [dcl.fct.default]/4:

... A default argument shall not be redefined by a later declaration (not even to the same value). [ Example:

...
void m() {
    void f(int, int);     // has no defaults
    f(4);                 // error: wrong number of arguments
    void f(int, int = 5); // OK
    f(4);                 // OK, calls f(4, 5);
    void f(int, int = 5); // error: cannot redefine, even to same value
}
...

end example ] ...

此外,正如@Sven 所注意到的,默认参数不应出现在typedef 中,尽管g++ 即使使用-pedantic 也无法捕获它。我想clangVisual C++拒绝这个,但我没试过。

关于c++ - 具有默认参数的 C++ 函数的多个声明,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/6708726/

相关文章:

c++ - 在没有任何干预的情况下继续运行程序,直到它被要求退出

c++ - 是否可以在实例方法中使用带有 "this"的重载运算符?

c++ - 使用 Boost.Log 和 Boost.ASIO 导致崩溃

c++11 - 融合改编的 std_tuple View ,转换为另一个元组

c++ - 在类声明中定义静态变量时未解析的外部符号

c++11 - C++11 标准中已弃用的 C++ 功能编译列表

c++ - 为什么模板类函数必须在同一个翻译单元中声明?

c++ - GPU 如何帮助改进迭代问题?

c++ - 基于范围的 for 和其他增量

c# - C# IL 在调用 C++ DLL 时如何通过 Ref 取回参数