在c語言中要用到,類似java中的ArrayList的功能,一般是怎麼做的?

小橋流水97455


在c語言中要用到,類似java中的ArrayList的功能,一般是怎麼做的?

1. 標準C肯定是沒有的,用第三方庫才能使用類似功能。

2. C++可以使用STL。

3. 可以自己實現一下C版本的ArrayList,畢竟Java對象可以轉為C結構體和成員指針,ArrayList本質也只是一個數組。

(注:C語言再規定合適的約束的前提下,也是可以面向對象編程的!)


一個簡單的C ArrayList的Demo實現

1. 文件結構:

ArrayList.h:頭文件

ArrayList.c:實現頭文件中的功能

ArrayListTest.c:測試


2.ArrayList.h

頭文件的基本框架:

#ifndef _ARRAYLIST_H
#define _ARRAYLIST_H
// 頭文件體
#endif

頭文件中應包含結構體定義,必要的宏定義,需要直接在其他文件中使用的函數的定義。

Java中的ArrayList是實現引用的數組,而不是對象的數組,在連續的存儲空間中存放的是引用,而不是對象實體,所以在實現的時候採用void**,那麼這樣實現的ArrayList將可以含有任意類型的變量,壞處就是需要在使用的時候人為的解析。

capacity是當前item_list申請的長度。

my_size是當前item_list中存放了多少個元素。之所以不用size是為了和接下來實現的size函數區別。

為實現通過結構體通過調用成員的方式調用函數,而不是直接通過函數名調用函數。在結構體中聲明函數指針用以調用函數。這樣就可以在ArrayList.c中將函數的作用域聲明為只有本文件可見,避免和其他庫函數函數名衝突。但是因為結構體中包含這個文件中函數的指針,仍然可以調用函數。

typedef struct ArrayList ArrayList;
struct ArrayList{
void** item_list;
int capacity;
int my_size;

// 函數指針
}

為實現函數指針的賦值,需要聲明初始化函數,在初始化函數中將函數指針賦值,所以這兩個函數就不能放到結構體中:

// create a new ArrayList
int init_ArrayList(ArrayList*);
// create a new ArrayList with specified capacity
int init_ArrayList_capacity(ArrayList*,int capacity);


3.ArrayList.c

包含頭文件,實現函數

因為這些函數無法知道是哪個結構體調用自己的,所以都需要將調用的結構體傳進去。


4.ArrayListTest.c

包含頭文件

調用的方式類似:

al.retainAll(&al,aap+3,11);

al.trimToSize(&al);


由於篇幅有限,完整的實現請參照Github倉庫的簡易demo:C-Wheel-ArrayList


Ruby呀


ArrayList的泛型功能,還是數組長度自增功能?如果是泛型,那做不了,不支持!

如果是自增長度,Java裡是每add一次檢查一下數組長度是否還有剩餘空間可用,如果不可用了,不夠長了,那就會新申請一個原來長度2倍的數組,並把原來的數組裡的內容拷貝到新數組裡!


列炮緩開局


兩個途徑:

1、自力更生,自己造一個,list就是鏈表。

2、去開源項目中挖一個。大部分開源項目都有list算法。

C靠積累,寫得多了就有了自己的庫。


光明右使8787


不熟悉Java的功能,C#類似的知道,用C也可以仿的。這個模擬的動態數組,用C語言實現,並不難,涉及語言特性和多線程的,沒必要自找麻煩去實現完整。高效的解決方案,是直接使用C++做編譯器,寫的基本上是C代碼,到相關部分就直接使用C++標凖庫即可——兩者的本質區別是編程思想不是語法,用C++編譯器寫C程序無妨的。


TonyDeng


c語言沒有這種容器,這種容器的本質是,當元素長度快達到數組的上限時(具體達到上限的多少,每種語言都有設定),就給數組擴容,申請更大容量的數組。c語言也可以封裝成這樣的容器,不過c語言沒有類的概念,封裝起來比較麻煩,一般用結構體來粗略表示類,結構體中包含一個函數(檢測數組實際元素長度,若超過容量的一半,執行擴容),數組,數組容量n


分享到:


相關文章: