开发者

Temporaries problem in C++

I have this piece of code that prints the content of a directory using Boost.Filesystem:

class Shell {
private:
    const string& command;
    const path& firstPath;
    const path& secondPath;
public:
    // constructor
    Shell(const string& _command, const path& _firstPath, const path& _secondPath = path()): command(_command), firstPath(_firstPath), secondPath(_secondPath) {}

    //destructor
    ~Shell() {}

    //execute commands
    void executeCommand()
    {
        if(command.compare("ls"))
        {
            ls();
        }
    }

    void ls()
    {
        if(exists(firstPath)) 
        {
            vector<path> vecPath;

            copy(directory_iterator(firstPath), directory_iterator(), back_inserter(vecPath));
            sort(vecPath.begin(), vecPath.end());
            for(vector<path>::iterator it = vecPath.begin(); it != vecPath.end(); ++it)
            {
           开发者_Go百科     cout << *it << endl;
            }
        }
    }
};


int main(int argc, char** argv) 
{
    path Path = "c:\\workspace";
    Shell shell("ls", Path); // GOOD
    // Shell shell("ls", "c:\\workspace");  BAD creates temporary !!
    shell.executeCommand();
}

If I send my second argument direclty as a const char* I know that it will create a temporary and my constructor argument will only be visible in the constructor, then its lost, because of the reference to temporary.

My question is, why isnt the same thing happening to the first argument, the string, because I am sending him also as a const char* directly, but the value isnt lost outside of the constructor ?


Shell shell("ls", Path); // BAD - just happens to work as you expected.

Undefined Behavior - Anything can happen, including acting like you expect. The memory allocated by the temporary just happened to not be overwritten in your case.


std::string *ref;

{ 
    std::string tmp("temp");
    ref = &ref;  // risky, need to keep lifetime of tmp in mind

    const char* const rawptr = ref->c_str(); // equivalent to tmp.c_str()

    tmp = "altered"; // *ref also modified, rawptr completely invalid
}
// *ref _and_ rawptr completely invalid.


Is there a specific reason why you store references instead of copies? By changing your class from

class Shell {
private:
    const string& command;
    const path& firstPath;
    const path& secondPath;
...

to

class Shell {
private:
    const string command;
    const path firstPath;
    const path secondPath;
...

you can avoid lot's of your problems and both cases will be correct. Why this is the case you can see in the answer of sehe

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜