为什么他们坚持在下面的例子中使用`extern`说明符?

时间:2017-02-21 20:02:10

标签: c++ language-lawyer c++17 linkage

[basic.link]/6(我的强调):

  

块范围中声明的函数名称,块范围外部声明声明的变量名称具有链接。   ...

static void f();
static int i = 0;

void g() {
    extern void f(); // internal linkage
    int i; // #2 i has no linkage
    {
        extern void f(); // internal linkage  <--
        extern int i; // #3 external linkage
    }
}

[basic.link]/7
...

namespace X {
    void p() {
        q(); // error: q not yet declared
        extern void q(); // q is a member of namespace X  <--
    }
    void middle() {
        q(); // error: q not yet declared
    }
    void q() { /* ... */ } // definition of X::q
}
void q() { /* ... */ } // some other, unrelated q

箭头指向的extern说明符不是必需的,因为上面用粗体字符突出显示的段落[basic.link] / 6中的第一句话。或者我错过了什么?

2 个答案:

答案 0 :(得分:1)

extern强调各自的评论,指出extern在某些情况下没有效果(由于该段中列出的规则)

在第一个示例中,f具有内部链接,尽管被声明为extern,因为它首先在名称空间范围内声明为static

在第二个例子中,extern对声明没有影响,因为q也在没有它的情况下在命名空间范围内声明(并且X::q优先于::q)。

答案 1 :(得分:1)

我认为这些例子可以避免一些看似合理但错误的想法。

在第6段中,可能希望f()具有外部链接,因为这是extern&#34;通常&#34; (即在文件范围内)意味着,但它实际上是内部链接,因为static声明更进一步。

在第7段中,有人可能希望extern void q();在{{1>}之外(或在松散的语音外部中)q()提供p(),因此可以调用在middle(),但这也不会发生。

如果没有extern关键字,两者仍然是正确的,但是对于期望extern意味着不同的人而言,这并不奇怪。