小男孩‘自慰网亚洲一区二区,亚洲一级在线播放毛片,亚洲中文字幕av每天更新,黄aⅴ永久免费无码,91成人午夜在线精品,色网站免费在线观看,亚洲欧洲wwwww在线观看

分享

0長度數(shù)組

 kylin_1983 2014-06-24
 0長度數(shù)組是個(gè)奇怪的東西, 下面的代碼(兩種形式之一)是可以通過編譯的.
                char buf[];
   或者
                char buf[0];
   有什么用處呢? 大家知道數(shù)組名其實(shí)是數(shù)組所在內(nèi)存的首地址, 那么0長度數(shù)組的名字,其實(shí)是在內(nèi)存某個(gè)地方中作了一個(gè)標(biāo)記, 在適合的時(shí)候?qū)⑦@個(gè)標(biāo)記后面的一段內(nèi)存作為這個(gè)數(shù)組的內(nèi)容. 貌似數(shù)組下標(biāo)溢出了,但是善于利用這點(diǎn)可以實(shí)現(xiàn)一個(gè)”變長”結(jié)構(gòu)體.

例如下面的代碼:



CODE:#include <stdio.h>
#include <stdlib.h>
#include <string.h>

static const size_t def_name_len = 32 ;
typedef struct __Name
{
        size_t index;
        size_t len;
        char buf[0];
} Name, *PName ;

Name * createName(size_t index, const char * strname)
{
        size_t len;        
        PName pname = NULL;
        
        if (strname == NULL)
        {
                len = def_name_len;
               
        else
        {
                len = strlen(strname);
        }
        
        pname = (PName) malloc( sizeof(Name) + len + 1);  
        
        if(pname == NULL) return NULL;

        pname->index = index;
        pname->len = len;
        pname->buf[0] = '\0';
        if (strname)  strncpy(pname->buf, strname, len+1);
        return pname;
}

void freeName(PName pname)
{
        if(pname == NULL) return;
        free(pname);
        pname = NULL;
}

int main()
{
        int i;

        PName namelist[4] = {
                createName(1, "name1"),
                createName(2, "name2"),
                createName(3, "name3"),
                createName(4, "name4"),
        };
        
        for(i=0; i<4; ++i)
        {
                if(namelist[i])
                        printf("index %u \t name: %s \n", namelist[i]->index, namelist[i]->buf);
        }
        for(i=0; i<4; ++i)
        {
                freeName(namelist[i]);
        }
        return 0;
}
struct __Name有三個(gè)成員size_t index; size_t len; char buf[0]; 但是sizeof(Name)的結(jié)果是8, 為什么呢?因?yàn)樯厦嬲f了,” 0長度數(shù)組的名字,其實(shí)是在內(nèi)存某個(gè)地方中作了一個(gè)標(biāo)記”, 所以不占空間, 上面代碼中的pname = (PName) malloc( sizeof(Name) + len + 1);  一行,申請了一個(gè)Name結(jié)構(gòu)體變量,然后這塊內(nèi)存后面緊跟了一塊長len+1的內(nèi)存,所以我們就可以用buf[0..len]來訪問這段內(nèi)存了. 圖示如下:



CODE:-------------------------------------------------------------------------
 index (4byte) | len (4byte)  |<------- len+1 byte -------->|
-------------------------------------------------------------------------
| <----------Name-------------->|                    
                                |<-----buf[len+1] ------------|
    可見, 原理用一句話來總結(jié),就是利用數(shù)組下標(biāo)”故意”溢出來訪問數(shù)組首地址后的內(nèi)存.

    本站是提供個(gè)人知識管理的網(wǎng)絡(luò)存儲(chǔ)空間,所有內(nèi)容均由用戶發(fā)布,不代表本站觀點(diǎn)。請注意甄別內(nèi)容中的聯(lián)系方式、誘導(dǎo)購買等信息,謹(jǐn)防詐騙。如發(fā)現(xiàn)有害或侵權(quán)內(nèi)容,請點(diǎn)擊一鍵舉報(bào)。
    轉(zhuǎn)藏 分享 獻(xiàn)花(0

    0條評論

    發(fā)表

    請遵守用戶 評論公約

    類似文章 更多