简体   繁体   中英

(Anonymous) Namespaces, Functions, and Header Files

Not sure if this question has been asked before. I searched around and couldn't find an exact answer for my scenario, but I may have missed it.

The issue: I have a namespace in a header file, and some function prototypes inside that namespace in the header:

namespace Foo{
    void SomeFunc();
    void SomeOtherFunc(int);
}

In the .cpp file, I want to define the functions in the namespace while also providing some protection to an random number generator they all rely on with an anonymous namespace:

namespace Foo{

    namespace{
        RNG rando = new RNG();
    }

    void SomeFunc(){
        //implementation
    }

    void SomeOtherFunc(){
        //implementation
    }
}

The issue I am having is that there is no guarantee that the prototypes in the header file match up to the functions I am defining in the cpp file. Everything in the namespace{} code block can just be something new added to the namespace.

In the above code examples, SomeOtherFunc() is implemented without an argument of type int, but its declaration says it takes some argument. In actuality, it seems I overloaded the SomeOtherFunc() signature.

I could use the following in the cpp file:

namespace Foo{

    namespace{
        RNG rando = new RNG();
    }

}
void Foo::SomeFunc(){
    //implementation
}

void Foo::SomeOtherFunc(int){
    //implementation
}

The compiler seems to enforce the relationship between the functions' declaration and implementation, which I like. But then the functions seemingly don't have access to the data inside the anonymous namespace.

Am I missing something here? Is there something I could do to resolve the issues I feel are present in this implementation? I am not very well-versed in using (anonymous) namespaces, and so I apologize if this seems basic.

Move the unnamed namespace out of the other namespace:

namespace{
    RNG rando = new RNG();
}

void Foo::SomeFunc(){
    //implementation
}

void Foo::SomeOtherFunc(int){
    //implementation
}

It can't be accessed outside the translation unit anyways.

The usual convention is to as far as I know is to declare the anonymous namespace at the start of the .cpp files. In your case your cpp file should look like this.

namespace{
   RNG rando = new RNG();
}

void Foo::SomeFunc(){
    //implementation
}

void Foo::SomeOtherFunc(int){
    //implementation
}

This way the functions should have access to rando.

The anonymous namespace is a red herring. You can ignore it, it's literally an implementation detail.

Yes, you can overload a function from the header in the .cpp file. However, if you would try to use the undefined half of the pair, you'd get a linker error.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM