关于c++ c_str()和data()

c_str()和data():生成一个const char*指针,指向一个临时数组。

有解释说c_str必然带‘\0’,至于data要不要带’\0’,这个标准没说。

    string str = "012345";

    cout<<"string.data() addr is ";
    printf("%p\n",str.data());                //地址相同
    cout<<"string.c_str() addr is ";
    printf("%p\n\n",str.c_str());             //地址相同

    cout<<"test the 0 in string.data() ";
    printf("%x\n",*(str.data()+6));           //输出0
    cout<<"test the 0 in in string.c_str() ";
    printf("%x\n",*(str.c_str()+6));          //输出0

关于c_str()返回的字符串指针指向的数组

引用这里 的解释:这个数组的数据是临时的,当有一个改变这些数据的成员函数被调用后,其中的数据就会失效。因此要么现用先转换,要么把它的数据复制到用户自己可以管理的内存中。

    const char* c;
    string s="1234";
    c = s.c_str();
    cout<//输出:1234
    s="abcd";
    cout<//输出:abcd
    //补充两个
    s="ab";                 //输出ab 对于比原来临时数组小的都会直接在原来临时数组上直接修改
    printf("%c\n",c[3]);    //输出d,也就是说ab字符串只是把临时数组覆盖了,在c[2]的位置置0
    s="abcde";              //输出ab,新开辟了内存,并且原来的p依然可以用
    s="a";                  //输出ab,此时是在新开辟的内存上进行写,所以指针p所指的依然存在

隐患:指针p很不稳定,所以在使用的时候最好copy在自己的内存中使用,strncpy和memcpy都可以。
这个隐患也可以参考这里的关于string类的c_str方法不当的使用方法

勿通过string::data、string::c_str返回指针修改string内容

这里中有提到,勿通过string::data、string::c_str返回指针修改string内容
也就是说data()和c_str()只供引用使用。而且一旦string内容变动,则必须重新获取该指针。string对象的赋值,必须使用符合string类规则的处理方式,比如构造、append、erase等函数进行。

    char *p = (char*)str.c_str();
    p[0]='p';
    cout<<"use point c_str() to change the str ";
    cout<<str<//此时s[0]已经被改变了

所以返回值是const char *,虽然通过强制转换可以修改,但是出于保护不建议这么做







参考

http://book.51cto.com/art/201311/419423.htm
http://blog.csdn.net/zhangwu416826/article/details/7826048
http://www.cnblogs.com/ziwuge/archive/2011/08/30/2159878.html
http://www.metsky.com/archives/582.html
http://www.cnblogs.com/qlwy/archive/2012/03/25/2416937.html

你可能感兴趣的:(c++)