Forward declaring a function in a namespace inside another function in that namespace

喜夏-厌秋 提交于 2021-01-27 04:51:08

问题


I have two source files, a.cpp and b.cpp. In a.cpp, I have a function, foo:

namespace ns { void foo() { std::cout << "foo!"; } }

In b.cpp, I have another function in namespace ns in which I'd like to prototype and call foo:

namespace ns
{

void bar()
{
    void foo();
    foo();       
}

}

While the above is syntactically valid, it leads the compiler to think that foo is in the global namespace (or at least that's what I've deduced from the linker errors I get when I do this). My first two ideas to fix that were void ns::foo(); and namespace ns { void foo(); }, but neither is valid. Is it possible to correctly prototype this function inside bar?

Note that I know I could simply move this to the file scope or a header file, there have been many questions asked about this, but I want to specifically prototype it inside another function. My compiler is MSVC 14.0 with the latest update.

EDIT: Based on some tests I've done and our discussion in the comments, I believe this is an MSVC bug. Compare:

namespace ns
{

void bar()
{
    void foo();   // link error, MSVC assumes global namespace
    foo();
}

void foo() { }

} // namespace ns

This fails, as stated previously. However, moving the prototype out of the function makes MSVC correctly place the prototyped function in the enclosing namespace:

namespace ns
{

void foo();   // all fine
void bar()
{
    foo();
}

void foo() { }

} // namespace ns

回答1:


The standard is clear about this point:

3.3.2/11: (..) Function declarations at block scope and variable declarations with the extern specifier at block scope refer to declarations that are members of an enclosing namespace (...)

Consequently:

void bar()
{
    void foo();   // should refer to ns::foo() according to 3.3.2/11
    foo();
}

and the linking should refer to the separately compiled function which has the same signature:

1.3.17 signature: <function> name, parameter type list , and enclosing namespace (if any) [Note: Signatures are used as a basis for name mangling and linking.—end note ]



来源:https://stackoverflow.com/questions/34559689/forward-declaring-a-function-in-a-namespace-inside-another-function-in-that-name

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!