stl string 内部数据类型及静态变量查看代码

#define private public
#define protected public

#include <stdio.h>
#include <string.h>
#include <fcntl.h>
#include <unistd.h>
#include <errno.h>
#include <iostream>  
#include <typeinfo>
#include <string>

using namespace std;

//打印内存 BEGIN
inline char hdigit(int n){return "0123456789abcdef"[n&0xf];};
#define LEN_LIMIT 32
#define SUBSTITUTE_CHAR '`'
int isValidPtr(const void*p, int len)
{
    if (!p) {
        return 0;
    }
    int ret = 1;
    int nullfd = open("/dev/random", O_WRONLY);
    if (write(nullfd, p, len) < 0) {
        ret = 0;
        /* Not OK */
    }
    close(nullfd);
    return ret;
}

static const char* dumpline(char*dest, int linelen, const char*src, const char*srcend)
{
    if(src>=srcend) {
        return 0;
    }
    int i;
    unsigned long s = (unsigned long)src;
    for(i=0; i<8; i++) {
        dest[i] = hdigit(s>>(28-i*4));
    }
    dest[8] = ' ';
    dest += 9;
    if (isValidPtr(src,linelen/4)) {
      for(i=0; i<linelen/4 ; i++) {
        if(src+i<srcend) {
            dest[i*3] = hdigit(src[i]>>4);
            dest[i*3+1] = hdigit(src[i]);
            //dest[i*3+2] = ((i+1+(unsigned long)src)&3)?' ':'|';
            dest[i*3+2] = ' ';
            dest[linelen/4*3+i] = src[i] >= ' ' && src[i] < 0x7f ? src[i] : SUBSTITUTE_CHAR;
        }else{
            dest[i*3] = dest[i*3+1] = dest[i*3+2] = dest[linelen/4*3+i] = '|';
        }
      }
    } else {
      strcpy(dest, "***cannot read***");
      i = linelen/4;
    }
    dest[linelen] = 0;
    return src+i;
}

void hexdump( const void *addr, unsigned len)
{
    int linelen=80;
    static char _buf[128];
    char*buf = _buf;//(char*)alloca(linelen+1); // alloca() causes the initialization to fail!!!!
    buf[linelen]=0;
    const char*start = (char*)addr;
    const char*cur = start;
    const char*end = start+len;
    while(!!(cur = dumpline(buf,linelen,cur,start+len)))
    {
        //write_log( filename, funcname, lineno, "%s",buf);
        printf("0x%s \n",buf);
    }
}
//打印内存 END 

void print_string_inner_type()
{
    //type 
    //string 里面用到的变量
    cout<<"typeid string::traits_type "<<typeid(string::traits_type).name()<<" sizeof:"<<sizeof(string::traits_type)<<endl;
    cout<<"typeid string::value_type "<<typeid(string::value_type).name()<<" sizeof:"<<sizeof(string::value_type)<<endl;
    cout<<"typeid string::allocator_type "<<typeid(string::allocator_type).name()<<" sizeof:"<<sizeof(string::allocator_type)<<endl;
    cout<<"typeid string::size_type "<<typeid(string::size_type).name()<<" sizeof:"<<sizeof(string::size_type)<<endl;
    cout<<"typeid string::difference_type "<<typeid(string::difference_type).name()<<" sizeof:"<<sizeof(string::difference_type)<<endl;
    cout<<"typeid string::reference "<<typeid(string::reference).name()<<" sizeof:"<<sizeof(string::reference)<<endl;
    cout<<"typeid string::const_iterator "<<typeid(string::const_iterator).name()<<" sizeof:"<<sizeof(string::const_iterator)<<endl;
    cout<<"typeid string::_Rep "<<typeid(string::_Rep).name()<<" sizeof:"<<sizeof(string::_Rep)<<endl;

    //variable
    string a("hello");
    string b(a);
    string::_Rep* st_rep;
    st_rep = a._M_rep();
    st_rep->_M_length;
    st_rep->_M_capacity;
    st_rep->_M_refcount;
    a._M_dataplus;
    a._M_dataplus._M_p;

    cout<<"a.c_str():"<<endl;
    hexdump(a.c_str(),a.length()+1);
    cout<<"_M_rep:"<<endl;
    hexdump(a._M_rep(),a.length()+sizeof(string::_Rep));

    printf("a._M_dataplus:%p\n",&a._M_dataplus);
    printf("a._M_dataplus._M_p:%p\n",a._M_dataplus._M_p);
    printf("a._M_rep():%p\n",st_rep);

    //b是通过a 拷贝构造生成,b指向的内存地址和a一样,不过 _M_refcount 的值会加一
    cout<<"b._M_rep:"<<endl;
    hexdump(b._M_rep(),b.length()+sizeof(string::_Rep));

    //b重新赋值,不在是a的引用,因此b指向地址和a不一样, a 的_M_refcount 会减一
    b="aaa";
    cout<<"After operator= a._M_rep:"<<endl;
    hexdump(a._M_rep(),a.length()+sizeof(string::_Rep));
    cout<<"After operator= b._M_rep:"<<endl;
    hexdump(b._M_rep(),b.length()+sizeof(string::_Rep));

    //未赋值的string对象,不会调用构造函数,会指向静态内存块的地址 string::_Rep::_S_empty_rep_storage
    string e,f;
    cout<<"string::_Rep::_S_empty_rep_storage[]:"<<endl;
    hexdump(string::_Rep::_S_empty_rep_storage,20);
    cout<<"e:"<<endl;
    hexdump(e._M_rep(),e.length()+sizeof(string::_Rep));
    cout<<"f:"<<endl;
    hexdump(f._M_rep(),f.length()+sizeof(string::_Rep));

    //static
    //string中用到的静态值
    cout<<"static string::_Rep::_S_max_size 0x"<<hex<<string::_Rep::_S_max_size<<" sizeof:"<<sizeof(string::_Rep::_S_max_size)<<endl;
    cout<<"static string::_Rep::_S_terminal 0x"<<hex<<string::_Rep::_S_terminal<<" sizeof:"<<sizeof(string::_Rep::_S_terminal)<<endl;
}

void test_nagetive_idx()
{
    //a[-1]
    char c[]={"abcdefgh"};
    char* d=&c[2];

    cout<<"c:"<<endl;
    hexdump(c,sizeof(c));

    printf("&d[-1]=%p,d[-1]=%c\n",&d[-1],d[-1]);
}

int main(int argc,char* argv[])
{
    print_string_inner_type();
    test_nagetive_idx();

    return 0;
}

chiyl@centos65 ~/Compile/test » make
g++ -g main.cpp -o test
chiyl@centos65 ~/Compile/test » ./test
typeid string::traits_type St11char_traitsIcE sizeof:1
typeid string::value_type c sizeof:1
typeid string::allocator_type SaIcE sizeof:1
typeid string::size_type m sizeof:8
typeid string::difference_type l sizeof:8
typeid string::reference c sizeof:1
typeid string::const_iterator N9__gnu_cxx17__normal_iteratorIPKcSsEE sizeof:8
typeid string::_Rep NSs4_RepE sizeof:24
a.c_str():
0x0220d028 68 65 6c 6c 6f 00 ||||||||||||||||||||||||||||||||||||||||||hello`||||||||||||||
_M_rep:
0x0220d010 05 00 00 00 00 00 00 00 05 00 00 00 00 00 00 00 01 00 00 00 ````````````````````
0x0220d024 00 00 00 00 68 65 6c 6c 6f |||||||||||||||||||||||||||||||||````hello|||||||||||
a._M_dataplus:0x7fff90869ae0
a._M_dataplus._M_p:0x220d028
a._M_rep():0x220d010
b._M_rep:
0x0220d010 05 00 00 00 00 00 00 00 05 00 00 00 00 00 00 00 01 00 00 00 ````````````````````
0x0220d024 00 00 00 00 68 65 6c 6c 6f |||||||||||||||||||||||||||||||||````hello|||||||||||
After operator= a._M_rep:
0x0220d010 05 00 00 00 00 00 00 00 05 00 00 00 00 00 00 00 00 00 00 00 ````````````````````
0x0220d024 00 00 00 00 68 65 6c 6c 6f |||||||||||||||||||||||||||||||||````hello|||||||||||
After operator= b._M_rep:
0x0220d040 03 00 00 00 00 00 00 00 03 00 00 00 00 00 00 00 00 00 00 00 ````````````````````
0x0220d054 00 00 00 00 61 61 61 |||||||||||||||||||||||||||||||||||||||````aaa|||||||||||||
string::_Rep::_S_empty_rep_storage[]:
0x00602be0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ````````````````````
e:
0x00602be0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ````````````````````
0x00602bf4 00 00 00 00 ||||||||||||||||||||||||||||||||||||||||||||||||````||||||||||||||||
f:
0x00602be0 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ````````````````````
0x00602bf4 00 00 00 00 ||||||||||||||||||||||||||||||||||||||||||||||||````||||||||||||||||
static string::_Rep::_S_max_size 0x3ffffffffffffff9 sizeof:8
static string::_Rep::_S_terminal 0x sizeof:1
c:
0x90869af0 61 62 63 64 65 66 67 68 00 |||||||||||||||||||||||||||||||||abcdefgh`|||||||||||
&d[-1]=0x7fff90869af1,d[-1]=b

标签: none



添加新评论