第10章:C23と将来の展望

この章で学ぶこと

  • C23の主要な新機能
  • 従来のGCC拡張からの標準化
  • 新しい型と構文
  • C言語の将来の方向性
  • ---

    10.1 C23概要

    ISO/IEC 9899:2024

    C23は2024年に正式に承認されました。正式名称はC24ですが、開発中の名称C23が広く使われています。

    主な変更点

  • typeoftypeof_unqual の標準化
  • constexpr オブジェクト
  • #embed プリプロセッサディレクティブ
  • _BitInt(N)
  • nullptrnullptr_t
  • 属性構文 [[]]
  • auto 型推論
  • 2の補数の義務化
  • ---

    10.2 typeof と typeof_unqual

    使用例

    int x = 42;
    typeof(x) y = x;              /* int y */
    typeof_unqual(const int) z;   /* int z */
    
    /* 複雑な型の簡略化 */
    int (*fp)(int, int);
    typeof(fp) fp2;  /* 同じ型の関数ポインタ */
    

    マクロでの活用

    #define swap(a, b) do {     \
        typeof(a) tmp = (a);    \
        (a) = (b);              \
        (b) = tmp;              \
    } while (0)
    

    ---

    10.3 constexpr オブジェクト

    定義

    コンパイル時に値が決定される定数。

    constexpr int SIZE = 100;
    constexpr double PI = 3.14159265358979;
    
    int arr[SIZE];  /* OK: constexprは配列サイズに使用可能 */
    

    #define との違い

  • 型安全
  • スコープあり
  • デバッグ可能
  • #define OLD_SIZE 100    /* 型なし、スコープなし */
    constexpr int SIZE = 100;  /* int型、ブロックスコープ可能 */
    

    ---

    10.4 #embed ディレクティブ

    バイナリファイルの埋め込み

    static const unsigned char icon[] = {
        #embed "icon.png"
    };
    
    static const char shader[] = {
        #embed "shader.glsl"
        , '\0'  /* 終端を追加 */
    };
    

    従来の方法との比較

    /* 従来: 外部ツールでCソースに変換 */
    /* xxd -i icon.png > icon.h */
    
    /* C23: 直接埋め込み */
    #embed "icon.png"
    

    ---

    10.5 _BitInt(N) 型

    任意幅整数

    _BitInt(128) big_num;
    unsigned _BitInt(256) huge_num;
    
    /* 最低幅は実装定義、通常 BITINT_MAXWIDTH まで */
    _BitInt(BITINT_MAXWIDTH) max_int;
    

    使用例

    _BitInt(128) a = 1;
    a <<= 100;  /* 128ビット左シフト */
    

    ---

    10.6 nullptr と nullptr_t

    NULL の問題

    #define NULL ((void *)0)  /* または 0 */
    
    void f(int);
    void f(int *);
    
    f(NULL);  /* どちらが呼ばれる?曖昧 */
    

    nullptr の導入

    #include <stddef.h>
    
    nullptr_t np = nullptr;
    
    void *p = nullptr;  /* OK */
    int i = nullptr;    /* エラー */
    
    f(nullptr);  /* f(int *) が呼ばれる */
    

    ---

    10.7 属性構文 [[]]

    標準属性

    [[noreturn]] void abort_program(void);
    [[deprecated("use new_func")]] void old_func(void);
    [[maybe_unused]] int debug_var;
    [[nodiscard]] int must_use_result(void);
    [[fallthrough]];  /* switch内で意図的なフォールスルー */
    [[reproducible]] double pure_calc(double x);
    [[unsequenced]] int no_side_effects(int x);
    

    GCC属性との共存

    /* C23 */
    [[nodiscard]] int important(void);
    
    /* GCC/Clang(引き続き使用可能) */
    __attribute__((warn_unused_result)) int important(void);
    

    ---

    10.8 その他の変更

    auto 型推論

    auto x = 42;          /* int */
    auto p = &x;          /* int * */
    auto f = func;        /* 関数ポインタ */
    

    ラベル前の宣言

    switch (x) {
        int local;  /* C23: OK */
    case 1:
        local = 1;
        break;
    }
    

    2の補数の義務化

    符号付き整数は2の補数表現が必須に。1の補数、符号絶対値は廃止。

    true/false のキーワード化

    /* C11以前: <stdbool.h> のマクロ */
    /* C23: 言語キーワード */
    bool b = true;  /* <stdbool.h> なしで使用可能 */
    

    ---

    10.9 将来の展望

    検討中の機能

  • パターンマッチング
  • 改良されたエラー処理
  • コルーチン

C++との関係

C23は多くの機能をC++から取り入れました:

  • constexpr
  • nullptr
  • auto
  • 属性構文

組み込み・システムプログラミング

C言語は引き続き以下の分野で重要:

  • OSカーネル
  • 組み込みシステム
  • ドライバ
  • セキュリティクリティカルなソフトウェア
  • ---

    10.10 この章のまとめ

    C23の主要機能

  • typeof / typeof_unqual
  • constexpr
  • #embed
  • _BitInt(N)
  • nullptr
  • [[]] 属性構文
  • auto 型推論
  • 移行のポイント

  • コンパイラサポートの確認
  • 段階的な導入
  • 後方互換性の維持

---

確認問題

問題1

constexprconst の違いは?

解答

  • constexpr: コンパイル時に値が決定。配列サイズなどに使用可能。
  • const: 実行時に初期化可能。修飾された変数は変更不可だが、配列サイズには使用不可(VLAになる)。

問題2

nullptrNULL の違いは?

解答

  • nullptr: 型安全なヌルポインタ定数。整数への暗黙変換なし。
  • NULL: (void *)0 または 0 のマクロ。整数との区別が曖昧。

問題3

#embed の利点は?

解答

バイナリファイルを直接Cソースに埋め込める。外部ツール(xxd等)が不要になり、ビルドプロセスが簡略化される。

---

おわりに

この教材では、C言語の規格レベルでの理解を目指しました。

学んだ内容:

  • 規格文書の読み方
  • 型システムの厳密な定義
  • オブジェクトと値の表現
  • 未定義動作の回避
  • 処理系定義動作と移植性
  • 厳密なエイリアシング規則
  • メモリモデル
  • 標準ライブラリの仕様
  • コンパイラ拡張
  • C23の新機能

規格に基づいた正しい理解は、移植可能で信頼性の高いコードを書くための基盤です。

C言語は50年以上の歴史を持ちながら、今も進化を続けています。規格を読み、理解し、正しく使いこなすことが、真のCプログラマーへの道です。