リストその2
リストを作ってみた( new と add だけ)
こんな感じの双方向リストを定義して、追加や削除を行う汎用的な関数を作ってみようと思う。
今のところ、追加のみ対応している。
こんな構造体のリストになっているけど、value は void 型のポインタとかにすれば汎用的になるのでは? と思っている。
typedef struct list { int value; struct list* next; struct list* prev; } intList;
全ソースはこんな感じ
1 // $Id: list_sample.c 34 2008-05-15 17:07:16Z sugamasao $ 2 #include <stdio.h> 3 #include <stdlib.h> 4 5 typedef struct list { 6 int value; 7 struct list* next; 8 struct list* prev; 9 } intList; 10 11 /* add */ 12 int addList(intList* list) { 13 intList* l; 14 l = (intList*)malloc(sizeof(intList)); 15 if (l == NULL) { 16 puts("領域確保に失敗したのだ"); 17 return -1; 18 } 19 20 list->next = l; 21 l->prev = list; 22 l->next = NULL; 23 return 0; 24 } 25 26 /* new */ 27 int intListNew(intList** list, int size) 28 { 29 int i = 0; 30 intList *tmp; 31 32 if(size < 1) { 33 puts("構造体の生成はしないのだ"); 34 return 1; 35 } 36 37 *list = (intList*)malloc(sizeof(intList)); 38 if (list == NULL) { 39 puts("メモリ確保失敗なのだ"); 40 return 1; 41 } 42 (*list)->next = NULL; 43 (*list)->prev = NULL; 44 45 /* 先頭以降のリストを生成する */ 46 tmp = *list; 47 for(i = 1; i < size; i++) { 48 addList(tmp); 49 tmp = tmp->next; 50 } 51 52 return 0; 53 } 54 55 /* main */ 56 int main(void) { 57 intList* list; // リストを保持するポインタ 58 59 intListNew(&list, 3); 60 61 /* お試し:値を代入してみる */ 62 { 63 int i = 0; 64 intList* tmp = list; // リストを保持するポインタ 65 for(i = 0; i < 3; i++) { 66 tmp->value = 10+i; 67 tmp = tmp->next; 68 } 69 } 70 /* お試し:取得した値を表示する */ 71 { 72 intList* tmp = list; // リストを保持するポインタ 73 int i; 74 for(i = 0; i < 3; i++) { 75 printf("list[%d] = %d\n", i, tmp->value); 76 tmp = tmp->next; 77 } 78 } 79 80 return 0; 81 } 82
ちなみに、実行するとこんな感じ。
sugamasao% gcc -Wall list_sample.c && ./a.out [/Users/sugamasao/dev_work/trunk/lang/c/list_sample]
list[0] = 10
list[1] = 11
list[2] = 12
とりあえず、今思いついている事リスト
- malloc は一カ所の関数にできるんじゃね?
- add は引数にvaleuに対する初期値を入れるといい感じじゃね?
- いやいや、そうすると関数が型に束縛されちゃうなー。int しか使えない、とか char だけ、とかだとイマイチありがたみがないし。
- あー、ということはここもなんらかのポインタにすれば良いか?
- 一応双方向リストということだけど、値の削除時くらいしか prev の使いどころを思いつかない。
- うーん、よくよく考えると削除時とか、値をキーにしたい場合、value の型が無いと走査できないのでは。
- 使う側で削除する list のポインタを貰うのは・・・ちょっと使い勝手が悪い感じがするが。そうする方がライブラリ側は楽できるか。
- このままだと、list 内の検索(走査)は無理っぽいか(value の型を汎用的にすると)
- 配列みたいに、5番目、とかで先頭から5番目の要素のアドレスが帰ってくるとかあると結構便利か。
というわけで
あまりに奥が深くて死にたくなりますね!