为了账号安全,请及时绑定邮箱和手机立即绑定

为什么在返回字符串的函数上调用c_str()无效?

为什么在返回字符串的函数上调用c_str()无效?

C++
森栏 2019-11-04 09:56:21
我有一个返回字符串的函数。但是,当我调用它并对其执行c_str()将其转换为const char *时,它只有在我首先将其存储到另一个字符串中时才起作用。如果我直接从函数中调用c_str(),它将垃圾值存储在const char *中。为什么会这样呢?感觉我在这里错过了一些非常基本的东西...string str = SomeFunction();const char* strConverted = str.c_str(); // strConverted stores the value of the string properlyconst char* charArray= SomeFunction().c_str(); // charArray stores garbage valuestatic string SomeFunction(){    string str;    // does some string stuff    return str;}
查看完整描述

3 回答

?
SMILET

TA贡献1796条经验 获得超4个赞

函数返回的值对象是临时的。的结果c_str()仅在临时生存期内有效。在大多数情况下,临时项的生存期到完整表达式的结尾(通常是分号)。


const char *p = SomeFunction();

printf("%s\n", p); // p points to invalid memory here.

解决方法是确保c_str()在完整表达式结束之前使用的结果。


#include <cstring>


char *strdup(const char *src_str) noexcept {

    char *new_str = new char[std::strlen(src_str) + 1];

    std::strcpy(new_str, src_str);

    return new_str;

}


const char *p = strdup(SomeFunction.c_str());

请注意,这strdup是POSIX函数,因此,如果您是支持POSIX的平台,那么它已经存在。


查看完整回答
反对 回复 2019-11-04
?
沧海一幻觉

TA贡献1824条经验 获得超5个赞

  1. 的“ string str”在方法SomeFunction()是在一个局部变量SomeFunction(),和仅存活的范围内SomeFunction();

  2. 由于该方法的返回类型SomeFunction()是字符串,而不是字符串的引用,因此在“ return str;”之后SomeFunction()将返回的值的副本,该副本str将作为临时值存储在内存中的某个位置,在调用后SomeFunction(),该临时价值将立即被销毁;

  3. “ string str = SomeFunction();”将存储返回SomeFunction()到字符串的临时值str,实际上是该值的副本并存储到str,分配了一个新的存储块,并且“ ”的调用后的生存期str大于返回的临时值。完成后,返回的临时值立即被销毁,内存由系统回收,但此值的副本仍存储在中。这就是为什么“ ”可以获取正确的值,实际上返回的是初始元素的指针(指向的字符串值的第一个元素存储地址),而不是返回的临时值;SomeFunction();SomeFunction()strconst char* strConverted = str.c_str();c_str()strstrSomeFunction()

  4. “ const char* charArray= SomeFunction().c_str();”是不同的,“ SomeFunction().c_str()”将返回返回的临时值的初始元素的指针(返回的临时字符串值的第一个元素内存地址),但是在调用之后SomeFunction(),返回的临时值被破坏,并且该内存地址由系统重用,charArray可以获取该内存地址的值,但不能获取您期望的值;


查看完整回答
反对 回复 2019-11-04
  • 3 回答
  • 0 关注
  • 688 浏览

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信