std::make_shared 作为默认参数无法编译
在 Visual C++(2008 和 2010)中,以下代码无法编译,并出现以下错误:
#include <memory>
void Foo( std::shared_ptr< int > test = ::std::make_shared< int >( 5 ) )
{
}
class P
{
void
Foo( std::shared_ptr< int > test = ::std::make_shared< int >( 5 ) )
{
}
};
错误 C2039: 'make_shared' : 不是 '`全局命名空间'' 的成员
错误 C3861: 'make_shared': 找不到标识符
它是抱怨 P::Foo() 而不是 ::Foo() 的定义。
有谁知道为什么 Foo() 有一个 std::make_shared 的默认参数是有效的,但 P::Foo() 却不是?
In Visual C++ (2008 and 2010), the following code does not compile with the following error:
#include <memory>
void Foo( std::shared_ptr< int > test = ::std::make_shared< int >( 5 ) )
{
}
class P
{
void
Foo( std::shared_ptr< int > test = ::std::make_shared< int >( 5 ) )
{
}
};
error C2039: 'make_shared' : is not a member of '`global namespace''
error C3861: 'make_shared': identifier not found
It is complaining about the definition of P::Foo() not ::Foo().
Does anybody know why it is valid for Foo() to have a default argument with std::make_shared but not P::Foo()?
如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。
绑定邮箱获取回复消息
由于您还没有绑定你的真实邮箱,如果其他用户或者作者回复了您的评论,将不能在第一时间通知您!
发布评论
评论(2)
它看起来像是编译器中的错误。以下是重现该问题所需的最少代码:
Visual C++ 2008 和 2010 均报告:
Comeau 对此代码没有任何问题。
It looks like a bug in the compiler. Here is the minimal code required to reproduce the problem:
Visual C++ 2008 and 2010 both report:
Comeau has no issues with this code.
我在自己的代码中遇到了似乎相同的问题。我将其归结为以下的最少代码:
这与 James McNellis 的示例略有不同 - 而且我认为,它强调了这样一个事实:默认参数初始化程序中的名称空间限定出了问题。
在这种情况下,defaultValue 和 fun 位于同一命名空间中,因此您可以轻松地从 N::defaultValue 中删除 N:: ,并且它可以工作。
如果 defaultValue 位于不同的命名空间中,您仍然可以通过使用 using 将其带入本地命名空间或编写本地转发模板函数来解决它,例如:
有点痛苦,但可行。我相信您可以在 make_shared 情况下使用此技术,尽管我还没有尝试过。
I hit what appears to be the same issue in my own code. The minimal code I boiled it down to was this:
This is slightly different to James McNellis example - and, I think, highlights the fact that it is the namespace qualification in the default argument initiliser where it goes wrong.
In this case defaultValue and fun are in the same namespace, so you can trivially remove N:: from N::defaultValue and it works.
If defaultValue is in a different namespace you can still workaround it by either bringing it into the local namespace with using, or writing a local forwarding template function, e.g.:
A bit of a pain, but workable. I believe you could use this technique in the make_shared case, although I haven't tried it.