C++ strange behavior with string's c_str() function

前端 未结 2 1993
名媛妹妹
名媛妹妹 2020-12-12 00:28

I am moving my project from Visual Studio 06 to 2010. While doing so, I have observed this behavior in my code. I have a Get string function that look like this:

<         


        
相关标签:
2条回答
  • in simple words

    std::string str = GetTheStr(); // -> this is a copy of strSomeStdString
    const char* PtrCStr = str.c_str(); // -> str is still alive, ok
    const char* PtrData = str.data(); // -> str is still alive, ok
    const char*ptr = (char *)GetTheStr().c_str(); // -> pointer to a temporary, bad
    

    use the lifetime of str to keep the data "alive"

    0 讨论(0)
  • 2020-12-12 00:46

    What's happening in the invalid case is that GetTheStr() is returning a temporary, then c_str() is returning a reference to its internal data, then the temporary goes out of scope and suddenly you have a dangling reference to storage that is no longer valid. When you assign the returned value of GetTheStr() to a named variable, the variable is still alive and the result of its c_str() is still pointing to valid data.

    Lifetimes of temporaries is something that varies between implementations. It is my understanding that a temporary lives for the entire statement (std::cout << GetTheStr().c_str() << endl; is technically valid to my understanding because the lifteime is required to last for the entire statement, but poorly written because it is relying on a very subtle aspect of lifetime); however, whether a temporary lives beyond that statement to the end of the scope or not is, to my understanding, implementation-defined. I'm probably going to be pilloried for this last paragraph (especially by people with more precise knowledge on the topic), but the short story is that well written code should be more explicit when the lifetime of an object needs to be extended; if you need to retain a reference to the internal data of an object, then it's always best to guarantee that there is a named variable referring to the object to ensure that the containing object's lifetime exceeds the lifetime of the usage of its internal data.

    0 讨论(0)
提交回复
热议问题