前回の内容 : データ構造 (7) 講義 色々な型と型変換 : 型のサイズ/型の昇格/キャスト char, int, double long int, short int, float, unsigned ... メモリを示すサイズが異なる => sizeof 動的メモリの確保 : malloc/free メモリ:連続して並んでいるセルの集まり C 言語の「変数」に対応している その変数がもっている値(データ)を保存する役割 # データは、値と型 # メモリそのものがもっているは「値」(に対応するビットパターン) # 型 : そのメモリに保存されている値を # どのように扱うか ? # # 型の情報は、データではなくコードにある # # コンパイル時は利用可能/実行時は型の情報はない # # 同じデータを不適切な型として利用してまう危険性がある メモリの確保しかた 変数宣言 ( をすると、メモリの一部が、確保される ) => コンパイル時に決める(柔軟性がない) 動的なメモリ確保 => 実行時 変数宣言 利点: 変数名で、メモリを操作(値の取り出しと代入) 後始末が自動的に行われる 欠点: コンパイル時に決める必要があるので、 サイズや個数が固定(柔軟性に欠ける) 動的なメモリ確保 利点: サイズや個数を、実行時に自由に決められる(柔軟性に富む) # malloc を使って確保 欠点: メモリに名前(変数名)がないので、 ポインタ値を保持 ポインタ値を保存する変数[ポインタ変数]に記憶させて、 それを介して、利用する必要がある 後始末を、自分でやる必要がある # free を使って解放する必要がある [今回の内容] 動的なデータ構造 実行時にサイズや構造が決まるようなデータを扱いたい => alloc を利用する事になる ! 前回は、配列サイズを動的.. NULL 型: (void *) : メモリなんだけど、何が入るかわからない型 => 必ず、「(void *) 以外の」ポインタ型にキャストして使う 値: (void *)0 : この値は、「有効でない事が保証されている」ポインタ値 => 「有効でない」事を表すための値 => これと比較して一致したら、「無効」と考える # NUL 文字 : '\0' => ちゃんとした値 ( 文字の値として有効 ) # 型 : char (int) # 値 : 0 ( '\0' ) # ASCII Code 表の 0 に対応する文字コード # => NULL と同様、「普通でない『文字』」として、 # 利用される ( 例: End Of String ) # # NULL ポインタ : ポインタ値だが、「『無効』なポインタ値」という意味 # => alloc が返す値をと比較する場合のみ利用する # # ポインタ値を返す関数で、「無効」を示す場合に使う # !! stdio.h の中で(#define で)定義されている # !! => いつでも(#include があれば)、 # !! 「NULL」で参照可能 動的なデータ型の例 List データが並んでいるもの: cf. 配列との違い 含まれるデータの個数 要素への参照(一定時間内) List 動的的に変更可能(追加/削除) 先頭から順に(シーケンシャル参照) 配列 宣言時に決まる(固定) どこからでも(ランダム参照) LinkedList Cell をつないで、リストを作る 先頭への挿入と先頭の削除ができる 要素を参照する場合は、順番にポインタを手繰る必要がある !! Cell そのものは、単なる構造体 !! 複数の Cell の間に ( next の値を常に次要素の Cellにする事により..) !! List に相当するデータ構造がつくられた !! その 「List への相当」を実現するために、 !! insetICell/removeICell !! という関数で、実現をしている !! !! !! 基本型(int,double 等)は !! !! 型宣言するだけで、その型を実現するコードは、組み込み(自分で作る必要はない) !! !! ユーザ型(自分で構造体やポインタ型)は、 !! !! 型宣言して(値の集合を決める)だけではだめで、 !! !! その値を操作する関数を対で実装する事で、 !! !! 「型」としての役割を果たす