コース一覧
    C言語中級 連結リスト・応用
    ノードを定義する

    C言語中級 連結リスト・応用

    C言語の連結リストと応用的なデータ操作を学び、実装でデータを扱うコースです。

    1
    連結リスト
    01. 配列の限界15分
    02. ノードを定義する15分
    03. 先頭に追加する15分
    04. リストを歩く15分
    05. 任意位置の挿入と削除15分
    06. リストを全解放する15分
    07. つくる リスト版成績管理15分
    08. 第5章クイズ10分
    2
    応用
    01. 動的な二次元配列15分
    02. コマンドライン引数15分
    03. バイナリ保存15分
    04. エラーの調べ方15分
    05. つくる 引数とバイナリ保存15分
    06. 第6章クイズ10分
    3
    総合制作
    01. リスト版を完成させる20分
    02. メモリバグ演習20分
    03. 自由拡張20分
    04. 完成と次のステップ10分

    ノードを定義する

    自分と同じ型を指すポインタ

    連結リストの部品を、ここではノードと呼びます。ノードは「1人分の値」と「次はこれ」という矢印を1本ずつ持ちます。学生1人分ならこうです。

    c

    struct Node {
        char name[32];
        int score;
        struct Node *next;
    };

    要点は next の型です。定義している途中の struct Node を、その定義の中で使っています。これを自己参照構造体と呼びます。

    なぜこれが書けるのかというと、next はノードそのものではなくポインタだからです。コンパイラは構造体の大きさを決めるために各メンバの大きさを足しますが、ポインタの大きさは指す先の中身と関係なく決まっています。だから struct Node の中身がまだ確定していなくても計算が止まりません。

    c

    struct Node {
        struct Node next;   /* これは通らない */
    };

    こちらは自分の大きさを求めるのに自分の大きさが要るので、決めようがありません。ノードをつなぐ矢印がポインタでなければならない理由は、書き方の作法ではなく、これです。

    ノードはヒープに作る

    ノードは、プログラムが動いている途中で1個ずつ増えていきます。何個できるかは実行してみるまで分かりません。前章で見たとおり、こういう相手はヒープに置きます。

    c

    struct Node *first = malloc(sizeof(struct Node));

    sizeof(struct Node) はノード1個分の大きさです。sizeof(struct Node *) と書くとポインタ1個分しか確保できないので、* の有無をここで間違えると、名前を書き込んだ時点で隣を壊します。

    確保したノードは、free を呼ぶまで生き続けます。関数を抜けても消えないという性質が、あとで「関数の中で作ったノードを呼び出し元へ返す」という書き方を支えます。

    つなぐのは代入1つ

    矢印を張るのは代入です。

    c

    first->next = second;
    second->next = NULL;

    first->next は (*first).next の省略形で、入門で見たとおりの記法です。最後のノードの next には NULL を入れます。これがリストの終わりの印になり、歩くときの止まる条件になります。

    矢印を入れ忘れたときに起きること

    next に何も入れないまま歩き始めると、そこには malloc が返した時点の中身、つまり意味のない値が残っています。その値をアドレスとみなして参照した瞬間にプログラムは落ちるか、もっと悪いことに落ちずに知らない場所を読み書きします。ノードを作ったら、値を入れるのと同じ手で next も必ず決める、という手順にしておくと、この事故は起きません。あとで書く追加関数を、確保から next の設定までを1か所に閉じ込めた形にするのは、そのためでもあります。

    では、ノードを2つ作って手でつないでみましょう。

    要件

    1. struct Node は name、score、next の3つのメンバを持つ
    2. next は struct Node へのポインタにする
    3. 2つのノードは malloc でヒープに確保する
    4. 2人目の next は終端を表す値にする
    5. 最後に確保した2つを free する

    ヒント

    確保する大きさはノード1個分です。ポインタ1個分ではありません

    名前は配列なので代入ではコピーできません。strcpy を使います

    終端の印は NULL です。stdio.h を読み込んでいれば使えます

    生田 陸人
    監修生田 陸人
    ゆめさくエンジニア / 現役ソフトウェアエンジニア監修者プロフィールを見る →
    編集 ゆめさく編集部·公開 2026/08/07

    関連レッスン

    • 先頭に追加する

      ポインタの付け替えで先頭に足せるようになります。

    • リストを歩く

      終端まで順にたどれるようになります。

    • 任意位置の挿入と削除

      前のノードをつなぎ替えて、途中の要素を出し入れできるようになります。

    • リストを全解放する

      順序を守って最後まで解放できるようになります。

    このレッスンに出てくる用語

    意味があいまいなまま進んだ語は、ここから読み直せます。

    • 連結リスト各要素が次の要素へのポインタを持つ構造。
    • リスト順序付きで複数の値を扱うデータ構造
    • ヒープ親が子より常に大きい(最大ヒープ)または小さい(最小ヒープ)木構造。
    • 関数処理に名前を付けて再利用できる単位
    main.c
    エディタを読み込んでいます

    メモ

    ノードを定義する

    ⌘S で保存