其他分享
首页 > 其他分享> > c – 命名空间内的Friend函数声明/定义

c – 命名空间内的Friend函数声明/定义

作者:互联网

考虑名称空间内的类.该类的定义声明了一个友元函数.

namespace Foo
{
    class Bar
    {
        friend void baz();
    };
}

根据我所知,这应该将baz()声明为最内层封闭命名空间的成员,即Foo.

因此,我期望baz()的以下定义是正确的:

void Foo::baz() { }

但是,GCC(4.7)给了我一个错误.

error: ‘void Foo::baz()’ should have been declared inside ‘Foo’

几种解决方案似乎有效:

>在课堂外声明baz().

namespace Foo
{
    void baz();

    class Bar
    {
        friend void baz();
    };
}

>在命名空间内定义baz().

namespace Foo
{
    class Bar
    {
        friend void baz();
    };
}
...
namespace Foo
{
    void baz() { }
}

>使用-ffriend-injection标志进行编译,从而消除错误.

这些解决方案似乎与我所知的C中的声明/定义的一般规则不一致.

为什么我必须两次声明baz()?
为什么定义在命名空间内只是合法的,而且使用范围解析运算符是非法的?
为什么标志会消除错误?

解决方法:

Why do I have to declare baz() twice?

因为friend声明没有在命名空间中提供函数的可用声明.它声明,如果该函数在该命名空间中声明,它将是一个朋友;如果你要在一个类中定义一个友元函数,那么它将通过依赖于参数的查找(但不是其他)可用,就好像它是在命名空间中声明的一样.

Why is the definition otherwise only legal inside a namespace, and illegal with the scope resolution operator?

因为它没有(正确地)在命名空间中声明,并且只有声明了函数才能在其命名空间之外定义(使用范围解析).

Why does the flag eliminate the error?

因为该标志导致friend声明充当命名空间中的声明.这是为了兼容C的古代方言(显然,一些现代编译器),这是标准行为.

标签:friend-function,c,namespaces
来源: https://codeday.me/bug/20190929/1831641.html