10

在查看GCC 的警告选项时,我遇到了-Waggregate-return

-Waggregate-return
如果定义或调用任何返回结构或联合的函数,则发出警告。(在可以返回数组的语言中,这也会引发警告。)


引发警告的小例子:

class foo{};
foo f(void){return foo{};}
int main(){}

$ g++ -std=c++0x -Waggregate-return -o main main.cpp
main.cpp:在函数'foo f()'中:
main.cpp:2:5:警告:函数返回一个聚合[-Waggregate-返回]


另一个不会引起警告的小例子:

#include <string>
std::string f(void){return "test";}
int main(){}

使用 -Waggregate-return 有什么好处?
为什么有人要被警告这一点?
另外,std::string 不是一个类吗?-为什么我不警告第二个示例中的“返回的聚合”?

4

2 回答 2

9

在@AlokSave 发表评论之后,这里是稍后编辑的答案:

三是此编译器标志的两种可能解释。由于有关它的文档很少,因此它的原始含义有些不清楚,但主要有两种可能的解释:

1) 警告用户返回聚合对象,让他知道如果返回聚合对象(分配在堆栈上),堆栈可能会溢出。

2)显然,一些旧的 C 编译器不支持返回聚合(你必须返回一个指针)。

这两个哪个是最好的,我很难判断。但是,可以在以下链接中找到有关此标志的更多相关信息:

http://bytes.com/topic/c/answers/644271-aggregate-return-warnings

https://lists.gnu.org/archive/html/bug-gnulib/2012-09/msg00006.html

引用后一个链接:

在我熟悉的 GNU 应用程序(Emacs、coreutils、...)中,我们只需禁用 -Waggregate-return。这是一个完全不合时宜的警告,因为它的动机是支持与不允许返回结构的 C 编译器的向后兼容性。那些编译器早已死去,不再具有实际意义。

于 2012-12-24T04:23:36.667 回答
5

聚合在 C 和 C++ 标准中定义。C 版本说(C99 6.2.5 Types/20-21):

结构类型描述了一个顺序分配的非空成员对象集(在某些情况下,一个不完整的数组),每个对象都有一个可选的指定名称和可能的不同类型。

[...]

算术类型和指针类型统称为标量类型。数组和结构类型统称为聚合类型。

C++ 版本说(N3485 8.5.1 [dcl.init.aggr]/1):

聚合是一个数组或一个类(第 9 条),没有用户提供的构造函数(12.1),没有用于非静态数据成员的大括号或等号初始化器(9.2),没有私有或受保护的非静态数据成员(第 11 条),没有基类(第 10 条),也没有虚函数(10.3)。

您的第二个示例(带有std::string)不会触发警告,因为std::string具有用户提供的构造函数;并且有私有数据成员。

我怀疑这个警告的存在是因为在 C 中返回聚合被认为是糟糕的风格;在那种语言中,最好传递一个 out 指针。我认为它不适用于 C++。但我无法用任何数据证实这一点。

于 2012-12-24T04:22:21.967 回答