我想知道在类型不完整的情况下使用std::function
是否有效,例如,在前向声明的情况下。
#include <iostream>
#include <functional>
struct S;
std::function<S(void)> m;
struct S {
S() { std::cout << "ctor\n"; }
~S() { std::cout << "dtor\n"; }
void foo() { std::cout << "foo\n";}
};
S goo() {
return S{};
}
int main() {
m = goo;
m().foo();
}
即使S
在声明m
时是不完整的,我也可以像声明完整类型一样声明返回类型(非指针返回类型)。此代码符合要求且工作正常,但我不确定这段代码是否符合标准。因为如果返回类型不是普通函数中的指针,就不能向前声明它(所以我不能为goo()
转发声明S
)。
你知道这是不是一个有效的标准代码吗?
1条答案
按热度按时间0x6upsns1#
你知道这是不是一个有效的标准代码吗?
这个程序是格式良好的,因为即使
S
在定义std::function<S(void)> m;
时是不完整的,std::function
也不要求S
是完整的类型,而是要求S
是返回类型的名称。来自
std::function
的文档:函数类模板提供了多态 Package 器,它概括了函数指针的概念。 Package 器可以存储、复制和调用任意的可调用对象,给定调用签名,允许函数成为第一类对象。
上述内容意味着模板参数应采用调用签名的形式。调用签名文档中有:
调用签名是返回类型的名称,后跟一个用括号括起来的逗号分隔的零个或多个参数类型的列表。
(着重号是我的)
正如我们所看到的,上面要求
S
是返回类型的名称,也就是说,它没有明确要求S
是完整的。换句话说,您给出的示例中的
S
满足此条件,因此它是有效的。