C語(yǔ)言編程C++柔性數(shù)組結(jié)構(gòu)示例講解
繞指柔—柔性數(shù)組
也許你從來(lái)沒(méi)有聽(tīng)說(shuō)過(guò)柔性數(shù)組(flexible array)這個(gè)概念,但是它確實(shí)是存在的。 C99 中,結(jié)構(gòu)體中的最后一個(gè)元素允許是未知大小的數(shù)組,這就叫做柔性數(shù)組成員。
柔性數(shù)組的特點(diǎn):
1.結(jié)構(gòu)中的柔性數(shù)組成員前面必須至少一個(gè)其他成員。
2.sizeof 返回的這種結(jié)構(gòu)大小不包括柔性數(shù)組的內(nèi)存。
3.包含柔性數(shù)組成員的結(jié)構(gòu)用malloc ()函數(shù)進(jìn)行內(nèi)存的動(dòng)態(tài)分配,并且分配的內(nèi)存應(yīng)該大于結(jié)構(gòu)的大小,以適應(yīng)柔性數(shù)組的預(yù)期大小
那我們?nèi)绾问褂媚?/p>
法一
#include<stdio.h> #include<stdlib.h> struct S { int a; int arr[];//未知大小 柔性數(shù)組成員 數(shù)組的大小是可以調(diào)整的 }; int main() { //我們?cè)趺撮_(kāi)辟呢 //包含柔性數(shù)組成員的結(jié)構(gòu)體的使用,要配合malloc這樣的動(dòng)態(tài)內(nèi)存分配內(nèi)存函數(shù)使用 struct S* ps = (struct S*)malloc(sizeof(struct S) + 5 * sizeof(int)); //我們?nèi)绾问褂媚? ps->a = 100; int i = 0; for (i = 0; i < 5; i++) { ps->arr[i] = i; } //還想擴(kuò)大呢 struct S* ptr = (struct S*)realloc(ps, sizeof(struct S) + 10 * sizeof(int));//先交給ptr,防止內(nèi)存調(diào)整失敗 if (ptr == NULL)//判斷是否開(kāi)辟成功 { printf("擴(kuò)容失敗\n"); return 0; } else { ps = ptr; for (int i = 5; i < 10; i++) { ps->arr[i] = i; } for (int i = 0; i < 10; i++) { printf("%d ", ps->arr[i] = i); } //用完就釋放 free(ps); ps = NULL; } return 0; }
法二
#include<stdio.h> #include<stdlib.h> struct S { int a; int* parr; }; int main() { //我們?cè)趺撮_(kāi)辟呢 struct S* ps = (struct S*)malloc(sizeof(struct S)); //我們?nèi)绾问褂媚? ps->a = 100; ps->parr = (int*)malloc(5 * sizeof(int)); int i = 0; for (i = 0; i < 5; i++) { ps->parr[i] = i; } //還想擴(kuò)大呢 int* ptr = (int*)malloc(10 * sizeof(int));//先交給ptr,防止內(nèi)存調(diào)整失敗 if (ptr == NULL)//判斷是否開(kāi)辟成功 { printf("擴(kuò)容失敗\n"); return 0; } else { ps->parr = ptr; for (int i = 5; i < 10; i++) { ps->parr[i] = i; } for (int i = 0; i < 10; i++) { printf("%d ", ps->parr[i] = i); } //用完就釋放 free(ps->parr); ps->parr = NULL; free(ps); ps = NULL; } return 0; }
那上面那個(gè)方法好一點(diǎn)呢
第一個(gè)好處是:方便內(nèi)存釋放
如果我們的代碼是在一個(gè)給別人用的函數(shù)中,你在里面做了二次內(nèi)存分配,并把整個(gè)結(jié)構(gòu)體返回給用戶。用戶調(diào)用free可以釋放結(jié)構(gòu)體,但是用戶并不知道這個(gè)結(jié)構(gòu)體內(nèi)的成員也需要free,所以你不能指望用戶來(lái)發(fā)現(xiàn)這個(gè)事。所以,如果我們把結(jié)構(gòu)體的內(nèi)存以及其成員要的內(nèi)存一次性分配好了,并返回給用戶一個(gè)結(jié)構(gòu)體指針,用戶做一次free就可以把所有的內(nèi)存也給釋放掉。
第二個(gè)好處是:這樣有利于訪問(wèn)速度
連續(xù)的內(nèi)存有益于提高訪問(wèn)速度,也有益于減少內(nèi)存碎片。(其實(shí),我個(gè)人覺(jué)得也沒(méi)多高了,反正你跑不了要用做偏移量的加法來(lái)尋址)
總結(jié)
第一種好,不好的話,要柔性數(shù)組干嗎?是不是
何意百煉剛,化為繞指柔
首先說(shuō)明一下我不軟弱,只是單純覺(jué)得這句詩(shī)好玩,我不認(rèn)為這首詩(shī)是軟弱的詩(shī)我有自己的見(jiàn)解。說(shuō)軟弱的只能說(shuō)不要你想的就是你想的。
以上就是C語(yǔ)言編程之柔性數(shù)組示例講解的詳細(xì)內(nèi)容,更多關(guān)于C語(yǔ)言柔性數(shù)組的資料請(qǐng)關(guān)注腳本之家其它相關(guān)文章!
相關(guān)文章
C語(yǔ)言實(shí)現(xiàn)快速排序改進(jìn)版
這篇文章主要為大家詳細(xì)介紹了C語(yǔ)言實(shí)現(xiàn)快速排序的改進(jìn)代碼,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-08-08C++11右值引用和std::move語(yǔ)句實(shí)例解析(推薦)
右值引用(及其支持的Move語(yǔ)意和完美轉(zhuǎn)發(fā))是C++0x將要加入的最重大語(yǔ)言特性之一。這篇文章主要介紹了C++11右值引用和std::move語(yǔ)句實(shí)例解析,非常不錯(cuò),具有參考借鑒價(jià)值,需要的朋友可以參考下2017-03-03linux c語(yǔ)言操作數(shù)據(jù)庫(kù)(連接sqlite數(shù)據(jù)庫(kù))
linux下c語(yǔ)言操作sqlite數(shù)據(jù)庫(kù)實(shí)例方法,大家參考使用吧2013-12-12C語(yǔ)言實(shí)現(xiàn)通訊錄系統(tǒng)
這篇文章主要為大家詳細(xì)介紹了C語(yǔ)言實(shí)現(xiàn)通訊錄系統(tǒng),文中示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2018-02-02用C++面向?qū)ο蟮姆绞絼?dòng)態(tài)加載so的方法
下面小編就為大家?guī)?lái)一篇用C++面向?qū)ο蟮姆绞絼?dòng)態(tài)加載so的方法。小編覺(jué)得挺不錯(cuò)的,現(xiàn)在就分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2016-12-12Windows安裝配置C/C++(VS2017)OpenSSL開(kāi)發(fā)環(huán)境配置教程
這篇文章主要為大家詳細(xì)介紹了Windows安裝配置C/C++,OpenSSL開(kāi)發(fā)環(huán)境配置教程,具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2017-07-07c語(yǔ)言簡(jiǎn)單實(shí)現(xiàn)文件 r/w 操作方法
由于在 C 語(yǔ)言中 '\' 一般是轉(zhuǎn)義字符的起始標(biāo)志,故在路徑中需要用兩個(gè) '\' 表示路徑中目錄層次的間隔,也可以使用 '/' 作為路徑中的分隔符,本文重點(diǎn)給大家介紹用c語(yǔ)言簡(jiǎn)單實(shí)現(xiàn)文件 r/w 操作方法,感興趣的朋友一起學(xué)習(xí)吧2021-05-05