简体   繁体   中英

Calling functions within namespaces

Is it possible to call a function within a namespace? I need to do this because the function assigns meaningful values to the variables. If not, is there a workaround? An idea of what I want is below, with foo the function within which the variables are assigned values, and bar1 , bar2 the two variables to be given values.

namespace space{
    bar *bar1;
    bar *bar2;

    void foo(bar *b1, bar *b2) {/*b1 and b2 and given values*/}
    foo(bar1, bar2); // this foo is a function call.
}

To clarify, bar1 and bar2 should be defined only the first time they are called and no other time.

This does, I believe, exactly what the OP wants, but it's horrible. Every CPP file that includes space.h is going to instantiate bar's 1 and 2 and init. Naming collision hell when the linker tries to sort it all out.

#ifndef SPACE_H
#define SPACE_H
#include <iostream>
namespace space
{
    class bar
    {
    public:
        // use your own stuff here. This is for sample use only.
        bar(const std::string & str):mStr(str)
        {

        }
        friend std::ostream &operator<<(std::ostream & out, const bar &bq)
        {
            out << bq.mStr;
            return out;
        }
    private:
        std::string mStr;
    };
    bar *bar1; // consider using std::unique_ptr in place of the raw pointer
    bar *bar2;

    class Init
    {
    public:
        Init()
        {
            bar1 = new bar("bar, bar, bar");
            bar2 = new bar("barbara anne");
        }
        virtual ~Init() // std::unique_ptr makes this destructor unnecessary
        {
             delete bar1;
             delete bar2;
        }
    }
    Init init; // init will construct and assign the bars before main 
               // and destruct and delete the bars when the program exits
}
#endif

static makes it marginally better static restricts each bar and init to each including CPP file, but now you have the variables duplicated in each including CPP file, more RAM use and changing one does not change the others.

    static bar *bar1;
    static bar *bar2;

    class Init
    {
    public:
        Init()
        {
            bar1 = new bar("bar, bar, bar");
            bar2 = new bar("barbara anne");
        }
        virtual ~Init()
        {
             delete bar1;
             delete bar2;
        }
    };
    static Init init;

Another tweak doesn't do exactly what OP wants, but it's close, a lot safer that take 1, and unified across compilation units unlike take 2. extern instructs the compiler to allow use of bars 1 and 2 without instantiating them, but that means someone has to actually allocate space for them.

    extern bar *bar1;
    extern bar *bar2;

    class Init
    {
    public:
        Init()
        {
            bar1 = new bar("bar, bar, bar");
            bar2 = new bar("barbara anne");
        }
        virtual ~Init()
        {
             delete bar1;
             delete bar2;
        }
    };

And a main CPP to demonstrate use

#include <iostream>
#include "space.h"

// allocate the bars and the Init object
space::bar *space::bar1; 
space::bar *space::bar2;

space::Init init;

int main()
{
    std::cout << *space::bar1 << std::endl;
    std::cout << *space::bar2 << std::endl;
    return 0;
}

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