From f1bb1e000ed0eaa46d27c6e18a757b4c066c3b4c Mon Sep 17 00:00:00 2001 From: na-trium-144 <100704180+na-trium-144@users.noreply.github.com> Date: Sun, 2 Aug 2026 00:29:41 +0900 Subject: [PATCH 1/9] =?UTF-8?q?=E7=94=A8=E8=AA=9E=E5=AE=9A=E7=BE=A9=20c++0?= =?UTF-8?q?,1=E9=80=94=E4=B8=AD?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/docs/cpp/0-intro/1-1-feature.md | 4 ++-- public/docs/cpp/0-intro/3-1-run.md | 2 ++ public/docs/cpp/0-intro/4-1-include.md | 2 ++ public/docs/cpp/0-intro/4-2-main.md | 3 +++ public/docs/cpp/0-intro/4-3-namespace.md | 6 +++--- public/docs/cpp/0-intro/5-0-summary.md | 4 ++-- public/docs/cpp/1-types-control/-intro.md | 2 +- public/docs/cpp/1-types-control/1-0-basic-types.md | 2 +- public/docs/cpp/1-types-control/2-0-uniform-init.md | 3 +++ public/docs/cpp/1-types-control/3-1-const.md | 2 +- public/docs/cpp/1-types-control/3-2-auto.md | 4 ++-- public/docs/cpp/1-types-control/4-0-console.md | 4 ++++ public/docs/cpp/1-types-control/6-0-summary.md | 4 ++-- public/docs/cpp/1-types-control/6-1-practice1.md | 2 +- public/docs/cpp/1-types-control/6-2-practice2.md | 2 +- public/docs/cpp/10-stl-containers/2-0-vector.md | 2 +- public/docs/cpp/10-stl-containers/3-0-map.md | 2 +- public/docs/cpp/11-stl-algorithms/3-0-lambda.md | 2 +- public/docs/cpp/11-stl-algorithms/4-2-practice2.md | 2 +- public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md | 2 +- public/docs/cpp/12-raii-smart-ptrs/4-1-practice1.md | 2 +- public/docs/cpp/12-raii-smart-ptrs/4-2-practice2.md | 2 +- public/docs/cpp/2-data-containers/1-0-string.md | 2 +- public/docs/cpp/2-data-containers/5-1-practice1.md | 2 +- public/docs/cpp/3-pointers/1-0-basic.md | 2 +- public/docs/cpp/3-pointers/1-1-address-operator.md | 2 +- public/docs/cpp/3-pointers/1-2-nullptr.md | 2 +- public/docs/cpp/3-pointers/4-1-stack.md | 2 +- public/docs/cpp/3-pointers/5-0-summary.md | 4 ++-- public/docs/cpp/4-functions/1-1-prototype-declaration.md | 2 +- public/docs/cpp/4-functions/1-2-void.md | 2 +- public/docs/cpp/4-functions/2-1-arg-by-value.md | 4 ++-- public/docs/cpp/4-functions/2-3-arg-by-reference.md | 2 +- public/docs/cpp/4-functions/4-0-summary.md | 2 +- public/docs/cpp/4-functions/4-1-practice1.md | 2 +- public/docs/cpp/5-project-build/1-0-header-and-source.md | 2 +- public/docs/cpp/5-project-build/1-2-split-example.md | 2 +- public/docs/cpp/5-project-build/2-0-include-guard.md | 2 +- public/docs/cpp/5-project-build/2-2-pragma-once.md | 2 +- public/docs/cpp/5-project-build/3-0-build.md | 2 +- public/docs/cpp/6-classes-basics/1-0-about.md | 2 +- public/docs/cpp/6-classes-basics/2-0-instance.md | 2 +- public/docs/cpp/6-classes-basics/3-0-access-control.md | 4 ++-- public/docs/cpp/6-classes-basics/5-1-practice1.md | 2 +- public/docs/cpp/6-classes-basics/5-2-practice2.md | 2 +- public/docs/cpp/7-classes-advanced/1-0-copy.md | 2 +- public/docs/cpp/7-classes-advanced/1-2-deep-copy.md | 2 +- public/docs/cpp/8-inheritance/5-1-practice1.md | 2 +- public/docs/cpp/8-inheritance/5-2-practice2.md | 2 +- public/docs/cpp/9-templates/1-1-function-template-detail.md | 2 +- public/docs/cpp/9-templates/2-1-class-template-detail.md | 2 +- 51 files changed, 69 insertions(+), 55 deletions(-) diff --git a/public/docs/cpp/0-intro/1-1-feature.md b/public/docs/cpp/0-intro/1-1-feature.md index fda0db0a..e90848f6 100644 --- a/public/docs/cpp/0-intro/1-1-feature.md +++ b/public/docs/cpp/0-intro/1-1-feature.md @@ -14,6 +14,6 @@ question: 他の言語と比較したC++の特徴は以下の通りです。 * **パフォーマンス 🚀:** C++は、OSやハードウェアに近い低レベルな操作が可能で、実行速度が非常に高速です。このため、パフォーマンスが最重要視される場面で絶大な信頼を得ています。 - * **静的型付け:** 変数の型はコンパイル時に決定されます。これにより、実行前に多くのエラーを発見でき、大規模な開発でもコードの安全性を保ちやすくなります。 + * **静的型付け:** [[変数]]の型は[[コンパイル]]時に決定されます。これにより、実行前に多くのエラーを発見でき、大規模な開発でもコードの安全性を保ちやすくなります。 * **マルチパラダイム:** 手続き型プログラミング、オブジェクト指向プログラミング、ジェネリックプログラミングなど、様々なプログラミングスタイルをサポートしています。これにより、問題の性質に合わせて最適なアプローチを選択できます。 - * **C言語との互換性:** C言語のコードの多くは、ほとんどそのままC++のコードとしてコンパイルできます。C言語で書かれた膨大なソフトウェア資産を活用できるのは大きな利点です。 + * **C言語との互換性:** C言語のコードの多くは、ほとんどそのままC++のコードとして[[コンパイル]]できます。C言語で書かれた膨大なソフトウェア資産を活用できるのは大きな利点です。 diff --git a/public/docs/cpp/0-intro/3-1-run.md b/public/docs/cpp/0-intro/3-1-run.md index b61641dd..09a22ed9 100644 --- a/public/docs/cpp/0-intro/3-1-run.md +++ b/public/docs/cpp/0-intro/3-1-run.md @@ -7,6 +7,8 @@ question: - コンパイルに失敗した場合、どのようなメッセージが表示されますか? - なぜPythonやJavaScriptはコンパイルが不要なのですか? - コンパイルすると、どのようなファイルが生成されますか? +term: + - コンパイル --- ### コンパイルと実行 diff --git a/public/docs/cpp/0-intro/4-1-include.md b/public/docs/cpp/0-intro/4-1-include.md index a6113935..f780c7a3 100644 --- a/public/docs/cpp/0-intro/4-1-include.md +++ b/public/docs/cpp/0-intro/4-1-include.md @@ -7,6 +7,8 @@ question: - iostreamがないとstd::coutは使えないのですか? - ヘッダファイルとは何ですか? - '#includeを書き忘れたらどうなりますか?' +term: + - インクルード --- ### `#include ` - ヘッダファイルのインクルード diff --git a/public/docs/cpp/0-intro/4-2-main.md b/public/docs/cpp/0-intro/4-2-main.md index 141871d2..19fe4d9b 100644 --- a/public/docs/cpp/0-intro/4-2-main.md +++ b/public/docs/cpp/0-intro/4-2-main.md @@ -7,6 +7,9 @@ question: - main関数は必ずint型を返さなければなりませんか? - return 0;と書かないとどうなりますか? - 引数を取るmain関数はどのような場合に使うのですか? +term: + - main関数 + - main 関数 --- ### `int main()` - main関数 diff --git a/public/docs/cpp/0-intro/4-3-namespace.md b/public/docs/cpp/0-intro/4-3-namespace.md index 70ce9640..afc587eb 100644 --- a/public/docs/cpp/0-intro/4-3-namespace.md +++ b/public/docs/cpp/0-intro/4-3-namespace.md @@ -12,7 +12,7 @@ question: ### `std::cout` と `std::endl` - 名前空間 (namespace) - * `std::cout`: "character output stream" の略で、コンソールへの標準出力を担当します。 + * [[`std::cout`]]: "character output stream" の略で、コンソールへの標準出力を担当します。 * `<<`: **ストリーム挿入演算子**と呼ばれ、右側のデータを左側のストリーム(ここでは `std::cout`)に流し込むイメージです。 - * `std::endl`: "end line" の略で、改行を出力し、出力バッファをフラッシュ(強制的に出力)します。 - * `std::`: `cout` や `endl` が `std` という**名前空間 (namespace)** に属していることを示します。名前空間は、大規模なプログラムで関数や変数の名前が衝突するのを防ぐための仕組みです。`std` はC++の標準ライブラリが定義されている名前空間です。 + * [[`std::endl`]]: "end line" の略で、改行を出力し、出力バッファをフラッシュ(強制的に出力)します。 + * `std::`: `cout` や `endl` が `std` という**名前空間 (namespace)** に属していることを示します。名前空間は、大規模なプログラムで関数や[[変数]]の名前が衝突するのを防ぐための仕組みです。`std` はC++の標準ライブラリが定義されている名前空間です。 diff --git a/public/docs/cpp/0-intro/5-0-summary.md b/public/docs/cpp/0-intro/5-0-summary.md index 07044ea2..19c949ce 100644 --- a/public/docs/cpp/0-intro/5-0-summary.md +++ b/public/docs/cpp/0-intro/5-0-summary.md @@ -8,8 +8,8 @@ question: [] ## この章のまとめ * C++は、**パフォーマンス**と**多機能性**を両立した強力なプログラミング言語です。 - * C++の開発フローは、「**ソースコード作成 → コンパイル → 実行**」が基本です。 - * すべてのC++プログラムは `main` 関数から実行が始まります。 + * C++の開発フローは、「**ソースコード作成 → [[コンパイル]] → 実行**」が基本です。 + * すべてのC++プログラムは [[`main` 関数]]から実行が始まります。 * `#include` で外部ライブラリの機能を読み込み、`namespace` で名前の衝突を避けます。 これであなたもC++プログラマの仲間入りです![[./next]]では、C++の根幹をなす型システムとメモリの仕組みについて学んでいきましょう。 diff --git a/public/docs/cpp/1-types-control/-intro.md b/public/docs/cpp/1-types-control/-intro.md index b6d09790..88c3de50 100644 --- a/public/docs/cpp/1-types-control/-intro.md +++ b/public/docs/cpp/1-types-control/-intro.md @@ -1 +1 @@ -C++は**静的型付け言語**です。PythonやJavaScriptのような動的型付け言語とは異なり、コンパイル時に変数の型が確定している必要があります。これにより、実行時のエラーを未然に防ぎ、高いパフォーマンスを実現します。 +C++は**静的型付け言語**です。PythonやJavaScriptのような動的型付け言語とは異なり、[[コンパイル]]時に[[変数]]の型が確定している必要があります。これにより、実行時のエラーを未然に防ぎ、高いパフォーマンスを実現します。 diff --git a/public/docs/cpp/1-types-control/1-0-basic-types.md b/public/docs/cpp/1-types-control/1-0-basic-types.md index 58e7801f..4f40866e 100644 --- a/public/docs/cpp/1-types-control/1-0-basic-types.md +++ b/public/docs/cpp/1-types-control/1-0-basic-types.md @@ -19,4 +19,4 @@ C++には多くの型がありますが、まずは以下の基本型を押さ * **文字型**: `char` (1バイト文字), `std::string` (文字列クラス。厳密には基本型ではありませんが、実用上必須) * **ブール型**: `bool` (`true` または `false`) -C++では変数のサイズ(ビット幅)が環境によって異なる場合がありますが、現代的な環境では `int` は32bit以上であることが保証されています。 +C++では[[変数]]のサイズ(ビット幅)が環境によって異なる場合がありますが、現代的な環境では `int` は32bit以上であることが保証されています。 diff --git a/public/docs/cpp/1-types-control/2-0-uniform-init.md b/public/docs/cpp/1-types-control/2-0-uniform-init.md index eaf2fa9c..682d91af 100644 --- a/public/docs/cpp/1-types-control/2-0-uniform-init.md +++ b/public/docs/cpp/1-types-control/2-0-uniform-init.md @@ -8,6 +8,9 @@ question: - int height{170.5}; のようにエラーになる方が安全とはどういうことですか? - int rough_height = 170.9; のように値が切り捨てられてしまうのは、問題ないのでしょうか? - 常に波括弧{}で初期化すれば良いのでしょうか? +term: + - 変数 + - 初期化 --- ## 変数の初期化:ユニフォーム初期化 `{}` diff --git a/public/docs/cpp/1-types-control/3-1-const.md b/public/docs/cpp/1-types-control/3-1-const.md index 107eea20..32cf0cde 100644 --- a/public/docs/cpp/1-types-control/3-1-const.md +++ b/public/docs/cpp/1-types-control/3-1-const.md @@ -12,7 +12,7 @@ question: ### `const`による不変性の保証 -`const` (constantの略) は、変数を**読み取り専用**にするためのキーワードです。一度`const`で初期化された変数の値は、後から変更しようとするとコンパイルエラーになります。 +`const` (constantの略) は、[[変数]]を**読み取り専用**にするためのキーワードです。一度`const`で初期化された[[変数]]の値は、後から変更しようとするとコンパイルエラーになります。 なぜ`const`が重要なのでしょうか? diff --git a/public/docs/cpp/1-types-control/3-2-auto.md b/public/docs/cpp/1-types-control/3-2-auto.md index 4e2991d1..4711390e 100644 --- a/public/docs/cpp/1-types-control/3-2-auto.md +++ b/public/docs/cpp/1-types-control/3-2-auto.md @@ -11,7 +11,7 @@ question: ### `auto`による型推論 -C++11から導入された`auto`キーワードを使うと、コンパイラが初期化式から変数の型を自動で推論してくれます。これにより、特に型名が長い場合にコードを簡潔に書くことができます。 +C++11から導入された`auto`キーワードを使うと、コンパイラが初期化式から[[変数]]の型を自動で推論してくれます。これにより、特に型名が長い場合にコードを簡潔に書くことができます。 ```cpp // autoを使わない場合 @@ -21,7 +21,7 @@ std::vector::iterator it = my_vector.begin(); auto it = my_vector.begin(); // コンパイラが it の型を std::vector::iterator と推論してくれる ``` -ただし、`auto`はあくまで「型を書く手間を省く」ものであり、変数が型を持たないわけではありません(動的型付け言語とは異なります)。初期化と同時に使う必要があり、型が明確な場面で適切に使うことが推奨されます。 +ただし、`auto`はあくまで「型を書く手間を省く」ものであり、[[変数]]が型を持たないわけではありません(動的型付け言語とは異なります)。初期化と同時に使う必要があり、型が明確な場面で適切に使うことが推奨されます。 ```cpp auto x = 10; // x は int型になる diff --git a/public/docs/cpp/1-types-control/4-0-console.md b/public/docs/cpp/1-types-control/4-0-console.md index 561331f6..c2fa0250 100644 --- a/public/docs/cpp/1-types-control/4-0-console.md +++ b/public/docs/cpp/1-types-control/4-0-console.md @@ -8,6 +8,10 @@ question: - std::endlは「バッファをフラッシュする」とありますが、バッファをフラッシュするとはどういうことですか? - キーボードから複数の値を入力する際、値と値の間はスペースで区切れば良いのですか? - 数値が期待される入力に対して文字列が入力された場合など、入力エラーへの対処はどうすれば良いですか? +term: + - std::cout + - std::cin + - std::endl --- ## コンソール入出力 (`std::cin`, `std::cout`) diff --git a/public/docs/cpp/1-types-control/6-0-summary.md b/public/docs/cpp/1-types-control/6-0-summary.md index 33660f2d..1e780998 100644 --- a/public/docs/cpp/1-types-control/6-0-summary.md +++ b/public/docs/cpp/1-types-control/6-0-summary.md @@ -8,7 +8,7 @@ question: [] ## この章のまとめ * **型システム**: `int`, `double`, `bool` などの基本型があり、静的に管理される。 - * **初期化**: `int x{10};` のような波括弧 `{}` を使う初期化が推奨される(縮小変換の防止)。 + * **初期化**: `int x{10};` のような波括弧 `{}` を使う[[初期化]]が推奨される(縮小変換の防止)。 * **型推論と定数**: `auto` で型推論を行い、変更しない変数には `const` を付ける。 - * **入出力**: `std::cout`, `std::cin` を使い、`<<`, `>>` 演算子でデータを流す。 + * **入出力**: [[`std::cout`]], [[`std::cin`]] を使い、`<<`, `>>` 演算子でデータを流す。 * **制御構文**: 基本は他言語と同じだが、`switch` のフォールスルー挙動などに注意する。 diff --git a/public/docs/cpp/1-types-control/6-1-practice1.md b/public/docs/cpp/1-types-control/6-1-practice1.md index 09779757..2a044055 100644 --- a/public/docs/cpp/1-types-control/6-1-practice1.md +++ b/public/docs/cpp/1-types-control/6-1-practice1.md @@ -10,7 +10,7 @@ question: ## 練習問題1:うるう年判定機 -西暦(整数)を変数 `year` に代入し、その年がうるう年かどうかを判定して結果を出力するプログラムを書いてください。 +西暦(整数)を[[変数]] `year` に代入し、その年がうるう年かどうかを判定して結果を出力するプログラムを書いてください。 > **うるう年の条件** > diff --git a/public/docs/cpp/1-types-control/6-2-practice2.md b/public/docs/cpp/1-types-control/6-2-practice2.md index cc886039..7eae9c5b 100644 --- a/public/docs/cpp/1-types-control/6-2-practice2.md +++ b/public/docs/cpp/1-types-control/6-2-practice2.md @@ -17,7 +17,7 @@ question: * 両方で割り切れるときは "FizzBuzz" と出力。 * それ以外は数値をそのまま出力。 -出力はスペース区切りまたは改行区切りどちらでも構いません。変数の初期化には `{}` を、ループカウンタの型には `auto` を使用してみてください。 +出力はスペース区切りまたは改行区切りどちらでも構いません。[[変数]]の[[初期化]]には `{}` を、ループカウンタの型には `auto` を使用してみてください。 ```cpp:practice2_2.cpp #include diff --git a/public/docs/cpp/10-stl-containers/2-0-vector.md b/public/docs/cpp/10-stl-containers/2-0-vector.md index cc732ba6..9ad608b8 100644 --- a/public/docs/cpp/10-stl-containers/2-0-vector.md +++ b/public/docs/cpp/10-stl-containers/2-0-vector.md @@ -20,7 +20,7 @@ question: * **高速なランダムアクセス**: インデックス(添字)を使って `[i]` の形式で要素に高速にアクセスできます (`O(1)`)。 * **末尾への高速な追加・削除**: `push_back()` や `pop_back()` を使った末尾への操作は非常に高速です。 -`std::vector`を使うには、``ヘッダをインクルードする必要があります。 +`std::vector`を使うには、``ヘッダを[[インクルード]]する必要があります。 ```cpp:vector_example.cpp #include diff --git a/public/docs/cpp/10-stl-containers/3-0-map.md b/public/docs/cpp/10-stl-containers/3-0-map.md index aec007bc..a93811f1 100644 --- a/public/docs/cpp/10-stl-containers/3-0-map.md +++ b/public/docs/cpp/10-stl-containers/3-0-map.md @@ -21,7 +21,7 @@ question: * **キーによる高速な検索**: キーに基づいて要素が自動的にソートされて格納されるため、検索、挿入、削除が高速です (`O(log n)`)。 * **一意なキー**: `std::map`内のキーは重複しません。同じキーで値を挿入しようとすると、既存の値が上書きされます。 -`std::map`を使うには、``ヘッダをインクルードする必要があります。 +`std::map`を使うには、``ヘッダを[[インクルード]]する必要があります。 ```cpp:map_example.cpp #include diff --git a/public/docs/cpp/11-stl-algorithms/3-0-lambda.md b/public/docs/cpp/11-stl-algorithms/3-0-lambda.md index 3373bab8..f5e1f049 100644 --- a/public/docs/cpp/11-stl-algorithms/3-0-lambda.md +++ b/public/docs/cpp/11-stl-algorithms/3-0-lambda.md @@ -21,7 +21,7 @@ question: [キャプチャ](引数リスト) -> 戻り値の型 { 処理本体 } ``` - * `[]` **キャプチャ句**: ラムダ式の外にある変数を取り込んで、式の中で使えるようにします。 + * `[]` **キャプチャ句**: ラムダ式の外にある[[変数]]を取り込んで、式の中で使えるようにします。 * `[]`: 何もキャプチャしない。 * `[=]`: 外の変数を全て値渡し(コピー)でキャプチャする。 * `[&]`: 外の変数を全て参照渡しでキャプチャする。 diff --git a/public/docs/cpp/11-stl-algorithms/4-2-practice2.md b/public/docs/cpp/11-stl-algorithms/4-2-practice2.md index 74dd06f2..b98f0ef6 100644 --- a/public/docs/cpp/11-stl-algorithms/4-2-practice2.md +++ b/public/docs/cpp/11-stl-algorithms/4-2-practice2.md @@ -15,7 +15,7 @@ question: 1. 正の偶数である要素の数 2. 負の奇数である要素の数 -**ヒント**: カウント用の変数を2つ用意し、ラムダ式のキャプチャ句で参照キャプチャ (`[&]`) して、式の中でインクリメントします。 +**ヒント**: カウント用の[[変数]]を2つ用意し、ラムダ式のキャプチャ句で参照キャプチャ (`[&]`) して、式の中でインクリメントします。 ```cpp:practice12_2.cpp #include diff --git a/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md b/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md index 998402ff..4a650000 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md +++ b/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md @@ -14,7 +14,7 @@ question: **RAII (Resource Acquisition Is Initialization)** は、「リソースの確保は、オブジェクトの初期化時に行い、リソースの解放は、オブジェクトの破棄時に行う」という設計パターンです。日本語では「リソース取得は初期化である」と訳されます。 -C++では、オブジェクトがそのスコープ(変数が宣言された `{}` の範囲)を抜けるときに、そのオブジェクトの**デストラクタ**が自動的に呼び出されます。この仕組みは、関数が正常に終了した場合だけでなく、**例外が投げられてスコープを抜ける場合でも保証されています**。 +C++では、オブジェクトがそのスコープ([[変数]]が宣言された `{}` の範囲)を抜けるときに、そのオブジェクトの**デストラクタ**が自動的に呼び出されます。この仕組みは、関数が正常に終了した場合だけでなく、**例外が投げられてスコープを抜ける場合でも保証されています**。 RAIIはこの性質を利用して、リソースの解放処理をデストラクタに記述することで、リソースの解放を自動化し、`delete` の呼び忘れや例外発生時のリソースリークを防ぎます。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/4-1-practice1.md b/public/docs/cpp/12-raii-smart-ptrs/4-1-practice1.md index 44fbe031..77311629 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/4-1-practice1.md +++ b/public/docs/cpp/12-raii-smart-ptrs/4-1-practice1.md @@ -11,7 +11,7 @@ question: `Employee` という名前のクラスを作成してください。このクラスは、コンストラクタで社員名を受け取って表示し、デストラクタで「(社員名) is leaving.」というメッセージを表示します。 -`main` 関数で、`"Alice"` という名前の `Employee` オブジェクトを `std::make_unique` で作成し、その `unique_ptr` を `promote_employee` という関数に渡してください。`promote_employee` 関数は `unique_ptr` を引数として受け取り(所有権が移動します)、「(社員名) has been promoted\!」というメッセージを表示します。 +[[`main` 関数]]で、`"Alice"` という名前の `Employee` オブジェクトを `std::make_unique` で作成し、その `unique_ptr` を `promote_employee` という関数に渡してください。`promote_employee` 関数は `unique_ptr` を引数として受け取り(所有権が移動します)、「(社員名) has been promoted\!」というメッセージを表示します。 プログラムを実行し、コンストラクタとデストラクタのメッセージが期待通りに表示されることを確認してください。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/4-2-practice2.md b/public/docs/cpp/12-raii-smart-ptrs/4-2-practice2.md index fbe22482..d104a2eb 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/4-2-practice2.md +++ b/public/docs/cpp/12-raii-smart-ptrs/4-2-practice2.md @@ -11,7 +11,7 @@ question: `Project` という名前のクラスを作成してください。コンストラクタでプロジェクト名を受け取り、デストラクタで「Project (プロジェクト名) is finished.」と表示します。 -`main` 関数で、`"Project Phoenix"` という名前の `Project` オブジェクトを `std::make_shared` で作成してください。 +[[`main` 関数]]で、`"Project Phoenix"` という名前の `Project` オブジェクトを `std::make_shared` で作成してください。 次に、`std::vector>` を作成し、作成した `shared_ptr` を2回 `push_back` してください。 その後、`shared_ptr` の参照カウント (`use_count()`) を表示してください。 最後に、`vector` を `clear()` して、再度参照カウントを表示してください。 diff --git a/public/docs/cpp/2-data-containers/1-0-string.md b/public/docs/cpp/2-data-containers/1-0-string.md index 79145b68..0d687ef7 100644 --- a/public/docs/cpp/2-data-containers/1-0-string.md +++ b/public/docs/cpp/2-data-containers/1-0-string.md @@ -17,7 +17,7 @@ C++では、標準ライブラリの `std::string` クラスを使用します **主な機能** - * **代入・初期化**: 文字列リテラルをそのまま代入可能。 + * **代入・[[初期化]]**: 文字列リテラルをそのまま代入可能。 * **結合**: `+` 演算子で結合可能。 * **比較**: `==`, `!=` などで中身の文字列比較が可能(C言語の `strcmp` は不要)。 * **サイズ取得**: `.size()` または `.length()` メソッドを使用。 diff --git a/public/docs/cpp/2-data-containers/5-1-practice1.md b/public/docs/cpp/2-data-containers/5-1-practice1.md index bcf567b8..fd65b12b 100644 --- a/public/docs/cpp/2-data-containers/5-1-practice1.md +++ b/public/docs/cpp/2-data-containers/5-1-practice1.md @@ -9,7 +9,7 @@ question: ### 練習問題1: 数値リストの統計 -`std::vector` を使用して、好きな整数を5つほど格納してください(コード内で直接初期化して構いません)。 +`std::vector` を使用して、好きな整数を5つほど格納してください(コード内で直接[[初期化]]して構いません)。 その後、範囲ベース for ループを使用して、その数値の「合計」と「最大値」を求めて出力するプログラムを作成してください。 ```cpp:practice3_1.cpp diff --git a/public/docs/cpp/3-pointers/1-0-basic.md b/public/docs/cpp/3-pointers/1-0-basic.md index 1061d10d..68b9a1f1 100644 --- a/public/docs/cpp/3-pointers/1-0-basic.md +++ b/public/docs/cpp/3-pointers/1-0-basic.md @@ -12,6 +12,6 @@ question: ポインタとは、変数の「値」ではなく、その変数がメモリ上の**どこにあるか(アドレス)**を格納する変数です。 -変数の型に応じて、対応するポインタの型が存在します。例えば、`int`型の変数のアドレスを格納するなら `int*` 型、`double`型の変数のアドレスを格納するなら `double*` 型のポインタを使います。アスタリスク `*` がポインタ型であることを示します。 +[[変数]]の型に応じて、対応するポインタの型が存在します。例えば、`int`型の変数のアドレスを格納するなら `int*` 型、`double`型の変数のアドレスを格納するなら `double*` 型のポインタを使います。アスタリスク `*` がポインタ型であることを示します。 > ポインタ変数の宣言時に `*` を型の横に付けるか、変数名の横に付けるかは好みが分かれますが、意味は同じです (`int* p;` と `int *p;` は等価)。このチュートリアルでは `int* p;` のように型の側に付けます。 diff --git a/public/docs/cpp/3-pointers/1-1-address-operator.md b/public/docs/cpp/3-pointers/1-1-address-operator.md index 5b1495c7..0acf0aee 100644 --- a/public/docs/cpp/3-pointers/1-1-address-operator.md +++ b/public/docs/cpp/3-pointers/1-1-address-operator.md @@ -11,7 +11,7 @@ question: ### アドレスと間接参照 - * **アドレス演算子 `&`**: 変数のメモリ上の住所(アドレス)を取得します。 + * **アドレス演算子 `&`**: [[変数]]のメモリ上の住所(アドレス)を取得します。 * **間接参照演算子 `*`**: ポインタが指し示している住所に行き、その中身(値)にアクセスします。 diff --git a/public/docs/cpp/3-pointers/1-2-nullptr.md b/public/docs/cpp/3-pointers/1-2-nullptr.md index 26e1af4b..3e9f8e69 100644 --- a/public/docs/cpp/3-pointers/1-2-nullptr.md +++ b/public/docs/cpp/3-pointers/1-2-nullptr.md @@ -11,7 +11,7 @@ question: ### `nullptr` の使用 ポインタが「どこも指していない」ことを示したい場合、C++では `nullptr` を使用します。 -古いC++やC言語では `NULL` や `0` が使われていましたが、モダンC++では型安全な `nullptr` を使うのが鉄則です。初期化されていないポインタは不定な場所を指すため、必ず初期化しましょう。 +古いC++やC言語では `NULL` や `0` が使われていましたが、モダンC++では型安全な `nullptr` を使うのが鉄則です。[[初期化]]されていないポインタは不定な場所を指すため、必ず初期化しましょう。 ```cpp:pointer_declaration.cpp #include diff --git a/public/docs/cpp/3-pointers/4-1-stack.md b/public/docs/cpp/3-pointers/4-1-stack.md index 22df4076..5db20992 100644 --- a/public/docs/cpp/3-pointers/4-1-stack.md +++ b/public/docs/cpp/3-pointers/4-1-stack.md @@ -10,6 +10,6 @@ question: ### スタック (Stack) - * これまでの変数は主にここに置かれます。 + * これまでの[[変数]]は主にここに置かれます。 * 関数のスコープ `{ ... }` を抜けると**自動的に消滅**します。 * 管理が楽で高速ですが、サイズに制限があります。 diff --git a/public/docs/cpp/3-pointers/5-0-summary.md b/public/docs/cpp/3-pointers/5-0-summary.md index f7868e23..f7972e2a 100644 --- a/public/docs/cpp/3-pointers/5-0-summary.md +++ b/public/docs/cpp/3-pointers/5-0-summary.md @@ -7,8 +7,8 @@ question: [] ## この章のまとめ -1. **ポインタ**はメモリアドレスを保持する変数。`&`で取得、`*`でアクセス。 -2. ポインタの初期化には `nullptr` を使う。 +1. **ポインタ**はメモリアドレスを保持する[[変数]]。`&`で取得、`*`でアクセス。 +2. ポインタの[[初期化]]には `nullptr` を使う。 3. **配列名**は先頭要素へのポインタとして振る舞う(減衰)。 4. `ptr + i` は、`ptr` の指す型 `i` 個分先のアドレスを指す。 5. **ヒープメモリ**は `new` で確保し、必ず `delete` で解放する。 diff --git a/public/docs/cpp/4-functions/1-1-prototype-declaration.md b/public/docs/cpp/4-functions/1-1-prototype-declaration.md index f0c03f5a..9e74c2e8 100644 --- a/public/docs/cpp/4-functions/1-1-prototype-declaration.md +++ b/public/docs/cpp/4-functions/1-1-prototype-declaration.md @@ -11,7 +11,7 @@ question: ### プロトタイプ宣言 -関数を `main` 関数の後に定義したい場合、事前に「こういう名前と引数の関数がありますよ」と宣言だけしておく必要があります。これを**プロトタイプ宣言**と呼びます。 +関数を [[`main` 関数]]の後に定義したい場合、事前に「こういう名前と引数の関数がありますよ」と宣言だけしておく必要があります。これを**プロトタイプ宣言**と呼びます。 ```cpp:declaration_intro.cpp #include diff --git a/public/docs/cpp/4-functions/1-2-void.md b/public/docs/cpp/4-functions/1-2-void.md index 549af6e1..af100af6 100644 --- a/public/docs/cpp/4-functions/1-2-void.md +++ b/public/docs/cpp/4-functions/1-2-void.md @@ -16,4 +16,4 @@ question: void printMessage(std::string message); ``` -[[./1]]で学んだように、`int`や`double`などの型は変数を定義するために使えましたが、`void`は「型がない」ことを示す特殊な型なので、`void my_variable;` のように変数を定義することはできません。あくまで関数の戻り値の型としてのみ使います。 +[[./1]]で学んだように、`int`や`double`などの型は[[変数]]を定義するために使えましたが、`void`は「型がない」ことを示す特殊な型なので、`void my_variable;` のように[[変数]]を定義することはできません。あくまで関数の戻り値の型としてのみ使います。 diff --git a/public/docs/cpp/4-functions/2-1-arg-by-value.md b/public/docs/cpp/4-functions/2-1-arg-by-value.md index 6dc83d56..f645251b 100644 --- a/public/docs/cpp/4-functions/2-1-arg-by-value.md +++ b/public/docs/cpp/4-functions/2-1-arg-by-value.md @@ -10,9 +10,9 @@ question: ### 1\. 値渡し (Pass by Value) -特に何も指定しない場合のデフォルトです。変数の**コピー**が作成され、関数に渡されます。 +特に何も指定しない場合のデフォルトです。[[変数]]の**コピー**が作成され、関数に渡されます。 - * **メリット:** 安全。関数内で値を変更しても、呼び出し元の変数には影響しない。 + * **メリット:** 安全。関数内で値を変更しても、呼び出し元の[[変数]]には影響しない。 * **デメリット:** コストが高い。巨大な配列やオブジェクトを渡す際、丸ごとコピーするためメモリと時間を浪費する。 diff --git a/public/docs/cpp/4-functions/2-3-arg-by-reference.md b/public/docs/cpp/4-functions/2-3-arg-by-reference.md index 69428ffa..aab88051 100644 --- a/public/docs/cpp/4-functions/2-3-arg-by-reference.md +++ b/public/docs/cpp/4-functions/2-3-arg-by-reference.md @@ -10,7 +10,7 @@ question: ### 3\. 参照渡し (Pass by Reference) -C++の真骨頂です。**「参照(Reference)」**とは、既存の変数に別の名前(エイリアス)をつける機能です。引数の型に `&` を付けるだけで宣言できます。 +C++の真骨頂です。**「参照(Reference)」**とは、既存の[[変数]]に別の名前(エイリアス)をつける機能です。引数の型に `&` を付けるだけで宣言できます。 * **メリット:** コピーが発生しない。**構文は「値渡し」と同じように書ける**(`*`や`&`を呼び出し側で意識しなくていい)。`nullptr` になることがないため安全性が高い。 * **デメリット:** 関数内で値を変更すると、呼び出し元も変わる(意図しない変更に注意)。 diff --git a/public/docs/cpp/4-functions/4-0-summary.md b/public/docs/cpp/4-functions/4-0-summary.md index ab95c027..51a2943b 100644 --- a/public/docs/cpp/4-functions/4-0-summary.md +++ b/public/docs/cpp/4-functions/4-0-summary.md @@ -9,7 +9,7 @@ question: [] * **プロトタイプ宣言**を使うことで、関数の定義順序に依存せずに記述できる。 * **値渡し**は安全だが、大きなオブジェクトではコピーコストがかかる。 - * **参照渡し (`&`)** は、ポインタのような効率性を持ちながら、変数のエイリアスとして直感的に扱える。 + * **参照渡し (`&`)** は、ポインタのような効率性を持ちながら、[[変数]]のエイリアスとして直感的に扱える。 * **`const` 参照渡し (`const T&`)** は、大きなデータを「読み取り専用」で効率的に渡すC++の定石である。 * **オーバーロード**により、同じ名前で異なる引数を受け取る関数を作れる。 * **デフォルト引数**で、呼び出し時の記述を省略できる。 diff --git a/public/docs/cpp/4-functions/4-1-practice1.md b/public/docs/cpp/4-functions/4-1-practice1.md index 7090b8ea..d8d23146 100644 --- a/public/docs/cpp/4-functions/4-1-practice1.md +++ b/public/docs/cpp/4-functions/4-1-practice1.md @@ -9,7 +9,7 @@ question: ### 練習問題1: 値の入れ替え(Swap) -2つの `int` 変数を受け取り、その値を入れ替える関数 `mySwap` を作成してください。 +2つの `int` [[変数]]を受け取り、その値を入れ替える関数 `mySwap` を作成してください。 ポインタではなく、**参照渡し**を使用してください。 ```cpp:practice5_1.cpp diff --git a/public/docs/cpp/5-project-build/1-0-header-and-source.md b/public/docs/cpp/5-project-build/1-0-header-and-source.md index 1c04d952..2273e003 100644 --- a/public/docs/cpp/5-project-build/1-0-header-and-source.md +++ b/public/docs/cpp/5-project-build/1-0-header-and-source.md @@ -20,4 +20,4 @@ C++では、プログラムを**ヘッダファイル**と**ソースファイ 1. **関心の分離**: インターフェース(何ができるか)と実装(どうやるか)を分離することで、コードの見通しが良くなります。他の開発者はヘッダファイルを見るだけで、その機能の使い方がわかります。 2. **コンパイル時間の短縮**: ソースファイルを変更した場合、再コンパイルはそのファイルだけで済みます。プロジェクト全体を再コンパイルする必要がないため、大規模なプロジェクトでは開発サイクルが劇的に速くなります。 -3. **再利用性の向上**: よく使う関数やクラスをまとめておけば、別のプロジェクトでそのファイルをインクルードするだけで簡単に再利用できます。 +3. **再利用性の向上**: よく使う関数やクラスをまとめておけば、別のプロジェクトでそのファイルを[[インクルード]]するだけで簡単に再利用できます。 diff --git a/public/docs/cpp/5-project-build/1-2-split-example.md b/public/docs/cpp/5-project-build/1-2-split-example.md index d78b168c..d3f501ab 100644 --- a/public/docs/cpp/5-project-build/1-2-split-example.md +++ b/public/docs/cpp/5-project-build/1-2-split-example.md @@ -32,7 +32,7 @@ int add(int a, int b) { } ``` -最後に、`main`関数を含むメインのソースファイルから、この`add`関数を呼び出します。 +最後に、[[`main`関数]]を含むメインのソースファイルから、この`add`関数を呼び出します。 ```cpp:math_app.cpp #include diff --git a/public/docs/cpp/5-project-build/2-0-include-guard.md b/public/docs/cpp/5-project-build/2-0-include-guard.md index a3363d2f..98e55531 100644 --- a/public/docs/cpp/5-project-build/2-0-include-guard.md +++ b/public/docs/cpp/5-project-build/2-0-include-guard.md @@ -10,7 +10,7 @@ question: ## インクルードガード -複数のファイルから同じヘッダファイルがインクルードされる状況はよくあります。例えば、`A.h`が`B.h`をインクルードし、ソースファイルが`A.h`と`B.h`の両方をインクルードするような場合です。 +複数のファイルから同じヘッダファイルが[[インクルード]]される状況はよくあります。例えば、`A.h`が`B.h`を[[インクルード]]し、ソースファイルが`A.h`と`B.h`の両方をインクルードするような場合です。 もしヘッダファイルに何の対策もしていないと、同じ内容(クラス定義や関数宣言)が複数回読み込まれ、「再定義」としてコンパイルエラーが発生してしまいます。 diff --git a/public/docs/cpp/5-project-build/2-2-pragma-once.md b/public/docs/cpp/5-project-build/2-2-pragma-once.md index 1913e227..3b9f6bab 100644 --- a/public/docs/cpp/5-project-build/2-2-pragma-once.md +++ b/public/docs/cpp/5-project-build/2-2-pragma-once.md @@ -20,4 +20,4 @@ question: std::string to_upper(const std::string& str); ``` -この一行をヘッダファイルの先頭に書くだけで、コンパイラがそのファイルが一度しかインクルードされないように処理してくれます。特別な理由がない限り、現在では `#pragma once` を使うのが主流です。 +この一行をヘッダファイルの先頭に書くだけで、コンパイラがそのファイルが一度しか[[インクルード]]されないように処理してくれます。特別な理由がない限り、現在では `#pragma once` を使うのが主流です。 diff --git a/public/docs/cpp/5-project-build/3-0-build.md b/public/docs/cpp/5-project-build/3-0-build.md index 510e29af..85c68744 100644 --- a/public/docs/cpp/5-project-build/3-0-build.md +++ b/public/docs/cpp/5-project-build/3-0-build.md @@ -10,6 +10,6 @@ question: ## プロジェクトのビルド -複数のソースファイル(`.cpp`)は、それぞれがコンパイルされて**オブジェクトファイル**(`.o` や `.obj`)になります。その後、**リンカ**がこれらのオブジェクトファイルと必要なライブラリを結合して、最終的な実行可能ファイルを生成します。 +複数のソースファイル(`.cpp`)は、それぞれが[[コンパイル]]されて**オブジェクトファイル**(`.o` や `.obj`)になります。その後、**リンカ**がこれらのオブジェクトファイルと必要なライブラリを結合して、最終的な実行可能ファイルを生成します。 この一連の作業を**ビルド**と呼びます。ファイルが増えてくると、これを手動で行うのは非常に面倒です。そこで、ビルド作業を自動化する**ビルドシステム**が使われます。 diff --git a/public/docs/cpp/6-classes-basics/1-0-about.md b/public/docs/cpp/6-classes-basics/1-0-about.md index 8b92d70d..88653354 100644 --- a/public/docs/cpp/6-classes-basics/1-0-about.md +++ b/public/docs/cpp/6-classes-basics/1-0-about.md @@ -13,7 +13,7 @@ question: 他のプログラミング言語でオブジェクト指向に触れたことがあるなら、「クラスはオブジェクトの設計図」という説明を聞いたことがあるかもしれません。C++でもその考え方は同じです。クラスは、ある「モノ」が持つべき**データ(属性)**と、そのデータに対する**処理(操作)**を一つにまとめたものです。 - - **データ(属性)**: クラス内に定義された変数のことで、**メンバ変数 (member variables)** または**データメンバ**と呼びます。 + - **データ(属性)**: クラス内に定義された[[変数]]のことで、**メンバ変数 (member variables)** または**データメンバ**と呼びます。 - **処理(操作)**: クラス内に定義された関数のことで、**メンバ関数 (member functions)** または**メソッド**と呼びます。 このように、関連するデータと処理を一つのクラスにまとめることを、OOPの重要な概念の一つである**カプセル化 (encapsulation)** と呼びます。💊 diff --git a/public/docs/cpp/6-classes-basics/2-0-instance.md b/public/docs/cpp/6-classes-basics/2-0-instance.md index 46b11360..32715d4d 100644 --- a/public/docs/cpp/6-classes-basics/2-0-instance.md +++ b/public/docs/cpp/6-classes-basics/2-0-instance.md @@ -12,7 +12,7 @@ question: クラスはあくまで「設計図」です。実際にプログラムで利用するためには、この設計図をもとに実体を作る必要があります。クラスから作られた実体のことを**オブジェクト (object)** または**インスタンス (instance)** と呼び、オブジェクトを作ることを**インスタンス化 (instantiation)** と言います。 -インスタンス化の構文は、変数の宣言とよく似ています。 +インスタンス化の構文は、[[変数]]の宣言とよく似ています。 ```cpp:instantiation.cpp #include diff --git a/public/docs/cpp/6-classes-basics/3-0-access-control.md b/public/docs/cpp/6-classes-basics/3-0-access-control.md index 1b39403a..ef4a3f84 100644 --- a/public/docs/cpp/6-classes-basics/3-0-access-control.md +++ b/public/docs/cpp/6-classes-basics/3-0-access-control.md @@ -11,7 +11,7 @@ question: ## アクセス制御: public と private による情報の隠蔽 -先ほどの`Person`クラスの例では、`main`関数から`taro.age = 30;`のようにメンバ変数に直接アクセスできました。これは手軽ですが、問題を引き起こす可能性があります。例えば、年齢にマイナスの値や非現実的な値を設定できてしまうかもしれません。 +先ほどの`Person`クラスの例では、[[`main`関数]]から`taro.age = 30;`のようにメンバ変数に直接アクセスできました。これは手軽ですが、問題を引き起こす可能性があります。例えば、年齢にマイナスの値や非現実的な値を設定できてしまうかもしれません。 ```cpp Person jiro; @@ -22,7 +22,7 @@ jiro.introduce(); このような意図しない操作を防ぐために、C++には**アクセス制御**の仕組みがあります。クラスのメンバは、外部からのアクセスの可否を指定できます。 - - **`public`**: クラスの外部(`main`関数など)から自由にアクセスできます。 + - **`public`**: クラスの外部([[`main`関数]]など)から自由にアクセスできます。 - **`private`**: そのクラスのメンバ関数からしかアクセスできません。外部からはアクセス不可です。 アクセス制御の基本は、**メンバ変数は`private`にし、メンバ関数は`public`にする**ことです。これにより、データの不正な書き換えを防ぎ、クラスの内部実装を外部から隠蔽します。これを**情報の隠蔽 (information hiding)** と呼び、カプセル化の重要な目的の一つです。 diff --git a/public/docs/cpp/6-classes-basics/5-1-practice1.md b/public/docs/cpp/6-classes-basics/5-1-practice1.md index 17b475dc..f1dda969 100644 --- a/public/docs/cpp/6-classes-basics/5-1-practice1.md +++ b/public/docs/cpp/6-classes-basics/5-1-practice1.md @@ -15,7 +15,7 @@ question: - メンバ変数は`private`で定義してください。 - コンストラクタで幅と高さを初期化できるようにしてください。 - 面積を計算して返す`getArea()`メソッドと、周の長さを計算して返す`getPerimeter()`メソッドを`public`で実装してください。 - - `main`関数で`Rectangle`クラスのインスタンスをいくつか生成し、面積と周の長さを表示するプログラムを作成してください。 + - [[`main`関数]]で`Rectangle`クラスのインスタンスをいくつか生成し、面積と周の長さを表示するプログラムを作成してください。 ```cpp:practice7_1.cpp #include diff --git a/public/docs/cpp/6-classes-basics/5-2-practice2.md b/public/docs/cpp/6-classes-basics/5-2-practice2.md index a3b149fd..e8f192bc 100644 --- a/public/docs/cpp/6-classes-basics/5-2-practice2.md +++ b/public/docs/cpp/6-classes-basics/5-2-practice2.md @@ -15,7 +15,7 @@ question: - メンバ変数は`private`で定義してください。 - コンストラクタで、タイトル、著者、ページ数を初期化できるようにしてください。 - 本の情報を整形してコンソールに出力する`printInfo()`メソッドを`public`で実装してください。(例: `Title: [タイトル], Author: [著者], Pages: [ページ数] pages`) - - `main`関数で`Book`クラスのインスタンスを生成し、その情報を表示してください。 + - [[`main`関数]]で`Book`クラスのインスタンスを生成し、その情報を表示してください。 ```cpp:practice7_2.cpp #include diff --git a/public/docs/cpp/7-classes-advanced/1-0-copy.md b/public/docs/cpp/7-classes-advanced/1-0-copy.md index 8cbe71cb..9dd1c6fe 100644 --- a/public/docs/cpp/7-classes-advanced/1-0-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-0-copy.md @@ -12,7 +12,7 @@ question: ## オブジェクトのコピー: コピーコンストラクタと代入演算子 -オブジェクトをコピーしたい場面は頻繁にあります。例えば、関数の引数にオブジェクトを渡すとき(値渡し)や、既存のオブジェクトで新しいオブジェクトを初期化するときなどです。 +オブジェクトをコピーしたい場面は頻繁にあります。例えば、関数の引数にオブジェクトを渡すとき(値渡し)や、既存のオブジェクトで新しいオブジェクトを[[初期化]]するときなどです。 ```cpp Vector2D v1(1.0, 2.0); diff --git a/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md b/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md index 3b36f3b0..524e2507 100644 --- a/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md @@ -126,7 +126,7 @@ Resource 10 destroyed. (at 0x139f065e0) | 機能 | いつ呼ばれるか | 何をするか | | :--- | :--- | :--- | -| **コピーコンストラクタ** | オブジェクトが**作られる時**に、他のオブジェクトで初期化される場合
`ResourceHolder r2 = r1;` | 新しいリソースを確保し、元のオブジェクトの**値**をコピーする。 | +| **コピーコンストラクタ** | オブジェクトが**作られる時**に、他のオブジェクトで[[初期化]]される場合
`ResourceHolder r2 = r1;` | 新しいリソースを確保し、元のオブジェクトの**値**をコピーする。 | | **コピー代入演算子** | **既にあるオブジェクト**に、他のオブジェクトを代入する場合
`r3 = r1;` | 1. 自分が持っている古いリソースを解放する。
2. 新しいリソースを確保し、元のオブジェクトの**値**をコピーする。 | このように、ポインタでリソースを管理するクラスでは、安全なコピーを実現するためにこの2つの関数を自分で定義することが不可欠です。 diff --git a/public/docs/cpp/8-inheritance/5-1-practice1.md b/public/docs/cpp/8-inheritance/5-1-practice1.md index de4b2741..682c08bc 100644 --- a/public/docs/cpp/8-inheritance/5-1-practice1.md +++ b/public/docs/cpp/8-inheritance/5-1-practice1.md @@ -11,7 +11,7 @@ question: `Vehicle` という親クラスを作成し、`move()` というメンバ関数を持たせましょう。次に、`Vehicle` を継承して `Car` クラスと `Motorcycle` クラスを作成し、それぞれが独自の `move()` の振る舞いをするようにオーバーライドしてください。 -`main` 関数では、`Vehicle` のポインタの配列を作成し、`Car` と `Motorcycle` のオブジェクトを格納して、ループでそれぞれの `move()` を呼び出してください。 +[[`main` 関数]]では、`Vehicle` のポインタの配列を作成し、`Car` と `Motorcycle` のオブジェクトを格納して、ループでそれぞれの `move()` を呼び出してください。 ```cpp:practice9_1.cpp #include diff --git a/public/docs/cpp/8-inheritance/5-2-practice2.md b/public/docs/cpp/8-inheritance/5-2-practice2.md index 4728cf91..995c02f0 100644 --- a/public/docs/cpp/8-inheritance/5-2-practice2.md +++ b/public/docs/cpp/8-inheritance/5-2-practice2.md @@ -16,7 +16,7 @@ question: 次に、`Employee` を継承して、`FullTimeEmployee`(月給制)と `PartTimeEmployee`(時給制)の2つのクラスを作成します。それぞれのクラスで `calculate_salary()` を具体的に実装してください。 -`main` 関数で、それぞれのクラスのインスタンスを作成し、給与が正しく計算されることを確認してください。 +[[`main` 関数]]で、それぞれのクラスのインスタンスを作成し、給与が正しく計算されることを確認してください。 ```cpp:practice9_2.cpp #include diff --git a/public/docs/cpp/9-templates/1-1-function-template-detail.md b/public/docs/cpp/9-templates/1-1-function-template-detail.md index 9bef5a84..8042ffd0 100644 --- a/public/docs/cpp/9-templates/1-1-function-template-detail.md +++ b/public/docs/cpp/9-templates/1-1-function-template-detail.md @@ -17,7 +17,7 @@ question: * **`template <...>`**: テンプレートの宣言を開始します。 * **`typename T`**: `T`という名前の「型引数」を定義しています。`typename`の代わりに`class`と書くこともできますが、意味は同じです。`T`は、このテンプレートが実際に使われるときに具体的な型(`int`や`double`など)に置き換えられます。 -`main`関数で`max_value(10, 20)`のように呼び出すと、コンパイラは引数の型が`int`であることから、`T`を`int`だと自動的に判断します(これを**テンプレート引数推論**と呼びます)。そして、内部的に以下のような`int`版の関数を生成してくれるのです。 +[[`main`関数]]で`max_value(10, 20)`のように呼び出すと、コンパイラは引数の型が`int`であることから、`T`を`int`だと自動的に判断します(これを**テンプレート引数推論**と呼びます)。そして、内部的に以下のような`int`版の関数を生成してくれるのです。 ```cpp // コンパイラが内部的に生成するコードのイメージ diff --git a/public/docs/cpp/9-templates/2-1-class-template-detail.md b/public/docs/cpp/9-templates/2-1-class-template-detail.md index bd0214d5..2590ee35 100644 --- a/public/docs/cpp/9-templates/2-1-class-template-detail.md +++ b/public/docs/cpp/9-templates/2-1-class-template-detail.md @@ -35,6 +35,6 @@ question: }; ``` - `Pair`と`Pair`は、コンパイルされると全く別のクラスとして扱われることに注意してください。 + `Pair`と`Pair`は、[[コンパイル]]されると全く別のクラスとして扱われることに注意してください。 クラステンプレートは、C++の強力なライブラリである**STL (Standard Template Library)**の根幹をなす技術です。[[./next]]で学ぶ`vector`や`map`といった便利なコンテナは、すべてクラステンプレートで実装されています。 From a564c1e80d9bb953a83513604b9563991eb255d6 Mon Sep 17 00:00:00 2001 From: na-trium-144 <100704180+na-trium-144@users.noreply.github.com> Date: Fri, 7 Aug 2026 23:13:55 +0900 Subject: [PATCH 2/9] =?UTF-8?q?=E7=94=A8=E8=AA=9E=E5=AE=9A=E7=BE=A9=20c++?= =?UTF-8?q?=201?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- public/docs/cpp/1-types-control/1-0-basic-types.md | 12 ++++++++++++ public/docs/cpp/1-types-control/2-0-uniform-init.md | 2 +- public/docs/cpp/1-types-control/3-1-const.md | 2 ++ public/docs/cpp/1-types-control/3-2-auto.md | 2 ++ public/docs/cpp/1-types-control/5-1-if.md | 2 ++ public/docs/cpp/1-types-control/5-2-switch.md | 7 ++++++- public/docs/cpp/1-types-control/5-3-loop.md | 5 +++-- public/docs/cpp/1-types-control/6-0-summary.md | 4 ++-- public/docs/cpp/1-types-control/6-2-practice2.md | 2 +- public/docs/cpp/11-stl-algorithms/2-3-foreach.md | 2 +- .../cpp/2-data-containers/4-0-range-based-for.md | 4 ++-- public/docs/cpp/2-data-containers/5-0-summary.md | 2 +- public/docs/cpp/2-data-containers/5-2-practice2.md | 2 +- public/docs/cpp/3-pointers/1-0-basic.md | 2 +- public/docs/cpp/3-pointers/2-0-array.md | 2 +- public/docs/cpp/3-pointers/3-0-legacy-string.md | 2 +- public/docs/cpp/3-pointers/5-1-practice1.md | 2 +- .../cpp/4-functions/2-4-arg-by-const-reference.md | 2 +- public/docs/cpp/7-classes-advanced/5-1-practice1.md | 2 +- 19 files changed, 42 insertions(+), 18 deletions(-) diff --git a/public/docs/cpp/1-types-control/1-0-basic-types.md b/public/docs/cpp/1-types-control/1-0-basic-types.md index 4f40866e..ede7093a 100644 --- a/public/docs/cpp/1-types-control/1-0-basic-types.md +++ b/public/docs/cpp/1-types-control/1-0-basic-types.md @@ -8,6 +8,18 @@ question: - charとstd::stringはどちらも文字を扱うのに使うようですが、違いは何ですか? - 変数のサイズが環境によって異なる場合があるとは、どういうことですか? - intが32bit以上であることが保証されているというのは、どういう意味ですか? +term: + - 基本型 + - 整数型 + - 浮動小数点型 + - 文字型 + - ブール型 + - int + - long + - double + - float + - char + - bool --- ## 基本的なデータ型 diff --git a/public/docs/cpp/1-types-control/2-0-uniform-init.md b/public/docs/cpp/1-types-control/2-0-uniform-init.md index 682d91af..b01572f8 100644 --- a/public/docs/cpp/1-types-control/2-0-uniform-init.md +++ b/public/docs/cpp/1-types-control/2-0-uniform-init.md @@ -17,7 +17,7 @@ term: C++には変数を初期化する方法がいくつもありますが、C++11以降では **波括弧 `{}` を使った初期化(ユニフォーム初期化)** が推奨されています。 -なぜ `{}` が良いのでしょうか? それは、**縮小変換(Narrowing Conversion)** を防げるからです。例えば、少数のデータを整数型変数に無理やり入れようとした時、`=` なら黙って切り捨てられますが、`{}` ならコンパイルエラーにしてくれます。 +なぜ `{}` が良いのでしょうか? それは、**縮小変換(Narrowing Conversion)** を防げるからです。例えば、小数のデータを[[整数型]]変数に無理やり入れようとした時、`=` なら黙って切り捨てられますが、`{}` ならコンパイルエラーにしてくれます。 ```cpp:initialization.cpp #include diff --git a/public/docs/cpp/1-types-control/3-1-const.md b/public/docs/cpp/1-types-control/3-1-const.md index 32cf0cde..b772469e 100644 --- a/public/docs/cpp/1-types-control/3-1-const.md +++ b/public/docs/cpp/1-types-control/3-1-const.md @@ -8,6 +8,8 @@ question: - constを付け忘れた場合、どのような問題が起こりうるのですか? - PIのように定数を宣言するとき、変数名を大文字にするのはルールですか? - constはどんなデータ型にでも使えるのですか? +term: + - const --- ### `const`による不変性の保証 diff --git a/public/docs/cpp/1-types-control/3-2-auto.md b/public/docs/cpp/1-types-control/3-2-auto.md index 4711390e..e4c4a195 100644 --- a/public/docs/cpp/1-types-control/3-2-auto.md +++ b/public/docs/cpp/1-types-control/3-2-auto.md @@ -7,6 +7,8 @@ question: - autoを使いすぎるとコードが読みにくくなることはありませんか? - auto z = "hello"; がconst char* になるのはなぜですか?std::stringにはならないのですか? - autoを使うことで、プログラムの実行速度に影響はありますか? +term: + - auto --- ### `auto`による型推論 diff --git a/public/docs/cpp/1-types-control/5-1-if.md b/public/docs/cpp/1-types-control/5-1-if.md index d8f3534b..9a5b356e 100644 --- a/public/docs/cpp/1-types-control/5-1-if.md +++ b/public/docs/cpp/1-types-control/5-1-if.md @@ -6,6 +6,8 @@ question: - if文の条件式はboolに変換可能なものである必要があるとありますが、具体的にどういうことですか? - if文の中にさらにif文を入れることはできますか? - else ifやelseは必ず書かないといけないものですか? +term: + - if --- ### `if`文 diff --git a/public/docs/cpp/1-types-control/5-2-switch.md b/public/docs/cpp/1-types-control/5-2-switch.md index 85c46481..859a6d74 100644 --- a/public/docs/cpp/1-types-control/5-2-switch.md +++ b/public/docs/cpp/1-types-control/5-2-switch.md @@ -8,11 +8,16 @@ question: - breakを書き忘れた場合、プログラムはどのように動作するのですか? - switch文のcaseに書ける値の型に制限はありますか? - defaultのcaseは必ず書くべきですか? +term: + - switch --- ### `switch`文とフォールスルー -`switch` 文は `break` を書かない限り、次の `case` へ処理が流れます(フォールスルー)。意図的なフォールスルーでない限り、`break` を忘れないように注意が必要です。C++17以降では `[[fallthrough]];` 属性をつけることで、「意図的なものである」とコンパイラに伝え、警告を抑制できます。 +`switch` 文は `break` を書かない限り、次の `case` へ処理が流れます(フォールスルー)。意図的なフォールスルーでない限り、`break` を忘れないように注意が必要です。 + +> [!TIP] +> C++17以降では `[[fallthrough]];` 属性をつけることで、「意図的なものである」とコンパイラに伝え、警告を抑制できます。 ```cpp:control-switch.cpp #include diff --git a/public/docs/cpp/1-types-control/5-3-loop.md b/public/docs/cpp/1-types-control/5-3-loop.md index 9d3e43c4..94345848 100644 --- a/public/docs/cpp/1-types-control/5-3-loop.md +++ b/public/docs/cpp/1-types-control/5-3-loop.md @@ -8,12 +8,13 @@ question: - whileループの具体的な使い方の例も見てみたいです。 - 無限ループを防ぐためにはどうすれば良いですか? - ループを途中で抜け出す方法や、次のイテレーションに進む方法はC++にもありますか? +term: + - while + - for --- ### ループ構文 -`while`, `for` も標準的です。 - ```cpp:control-loop.cpp #include diff --git a/public/docs/cpp/1-types-control/6-0-summary.md b/public/docs/cpp/1-types-control/6-0-summary.md index 1e780998..25f4edd7 100644 --- a/public/docs/cpp/1-types-control/6-0-summary.md +++ b/public/docs/cpp/1-types-control/6-0-summary.md @@ -7,8 +7,8 @@ question: [] ## この章のまとめ - * **型システム**: `int`, `double`, `bool` などの基本型があり、静的に管理される。 + * **型システム**: `int`, `double`, `bool` などの[[基本型]]があり、静的に管理される。 * **初期化**: `int x{10};` のような波括弧 `{}` を使う[[初期化]]が推奨される(縮小変換の防止)。 - * **型推論と定数**: `auto` で型推論を行い、変更しない変数には `const` を付ける。 + * **型推論と定数**: [[`auto`]] で型推論を行い、変更しない変数には [[`const`]] を付ける。 * **入出力**: [[`std::cout`]], [[`std::cin`]] を使い、`<<`, `>>` 演算子でデータを流す。 * **制御構文**: 基本は他言語と同じだが、`switch` のフォールスルー挙動などに注意する。 diff --git a/public/docs/cpp/1-types-control/6-2-practice2.md b/public/docs/cpp/1-types-control/6-2-practice2.md index 7eae9c5b..00efb17e 100644 --- a/public/docs/cpp/1-types-control/6-2-practice2.md +++ b/public/docs/cpp/1-types-control/6-2-practice2.md @@ -17,7 +17,7 @@ question: * 両方で割り切れるときは "FizzBuzz" と出力。 * それ以外は数値をそのまま出力。 -出力はスペース区切りまたは改行区切りどちらでも構いません。[[変数]]の[[初期化]]には `{}` を、ループカウンタの型には `auto` を使用してみてください。 +出力はスペース区切りまたは改行区切りどちらでも構いません。[[変数]]の[[初期化]]には `{}` を、ループカウンタの型には [[`auto`]] を使用してみてください。 ```cpp:practice2_2.cpp #include diff --git a/public/docs/cpp/11-stl-algorithms/2-3-foreach.md b/public/docs/cpp/11-stl-algorithms/2-3-foreach.md index 6c21dfde..d48adec7 100644 --- a/public/docs/cpp/11-stl-algorithms/2-3-foreach.md +++ b/public/docs/cpp/11-stl-algorithms/2-3-foreach.md @@ -10,7 +10,7 @@ question: ### `std::for_each`: 各要素に処理を適用する -指定された範囲の全ての要素に対して、特定の関数(処理)を適用します。ループを書くよりも意図が明確になる場合があります。 +指定された範囲の全ての要素に対して、特定の関数(処理)を適用します。 [[`for`]] ループを書くよりも意図が明確になる場合があります。 ```cpp // 3番目の引数に関数を渡す diff --git a/public/docs/cpp/2-data-containers/4-0-range-based-for.md b/public/docs/cpp/2-data-containers/4-0-range-based-for.md index d4c64f31..dfff2c64 100644 --- a/public/docs/cpp/2-data-containers/4-0-range-based-for.md +++ b/public/docs/cpp/2-data-containers/4-0-range-based-for.md @@ -12,7 +12,7 @@ question: ## 範囲ベース `for` ループ (Range-based for) -`std::vector` や `std::array` の中身を順番に処理する場合、インデックス `i` を使った `for (int i = 0; i < n; ++i)` は書くのが面倒ですし、境界外アクセスのリスクがあります。 +`std::vector` や `std::array` の中身を順番に処理する場合、インデックス `i` を使った [[`for`]] 文 (`for (int i = 0; i < n; ++i)`) は書くのが面倒ですし、境界外アクセスのリスクがあります。 モダンC++では、PythonやC\#の `foreach` に相当する **範囲ベース for ループ** が使えます。 @@ -22,7 +22,7 @@ for (要素の型 変数名 : コンテナ) { } ``` -ここで便利なのが、**`auto` キーワード**です。`auto` を使うと、コンパイラが型を自動推論してくれるため、型名を詳しく書く必要がなくなります。 +ここで便利なのが、**[[`auto`]] キーワード**です。`auto` を使うと、コンパイラが型を自動推論してくれるため、型名を詳しく書く必要がなくなります。 ```cpp:range_for_demo.cpp #include diff --git a/public/docs/cpp/2-data-containers/5-0-summary.md b/public/docs/cpp/2-data-containers/5-0-summary.md index f35a4848..7efe3570 100644 --- a/public/docs/cpp/2-data-containers/5-0-summary.md +++ b/public/docs/cpp/2-data-containers/5-0-summary.md @@ -10,6 +10,6 @@ question: [] 1. **文字列**: `char*` ではなく `std::string` を使う。結合や比較が簡単で安全。 2. **動的配列**: データの増減がある場合は `std::vector` を使う。`push_back()` で追加できる。 3. **固定配列**: サイズ固定の場合は `std::array` を使う。Cスタイル配列のモダンな代替。 -4. **ループ**: コンテナの全要素走査には「範囲ベース for ループ」と `auto` を使うとシンプルに書ける。 +4. **ループ**: コンテナの全要素走査には「範囲ベース for ループ」と [[`auto`]] を使うとシンプルに書ける。 これらの「標準ライブラリ(STL: Standard Template Library)」のコンテナを活用することで、メモリ管理の苦労を飛ばして、アプリケーションのロジックに集中できるようになります。 diff --git a/public/docs/cpp/2-data-containers/5-2-practice2.md b/public/docs/cpp/2-data-containers/5-2-practice2.md index 25b13fe8..950c155f 100644 --- a/public/docs/cpp/2-data-containers/5-2-practice2.md +++ b/public/docs/cpp/2-data-containers/5-2-practice2.md @@ -9,7 +9,7 @@ question: ### 練習問題2: 単語のフィルタリング 以下の単語リスト `words` の中から、**文字数(長さ)が5文字より大きい単語だけ**を選んで表示するプログラムを作成してください。 -(ヒント:`std::string` の `.size()` または `.length()` メソッドと `if` 文を使用します) +(ヒント:`std::string` の `.size()` または `.length()` メソッドと [[`if`]] 文を使用します) ```cpp:practice3_2.cpp #include diff --git a/public/docs/cpp/3-pointers/1-0-basic.md b/public/docs/cpp/3-pointers/1-0-basic.md index 68b9a1f1..aea22cce 100644 --- a/public/docs/cpp/3-pointers/1-0-basic.md +++ b/public/docs/cpp/3-pointers/1-0-basic.md @@ -12,6 +12,6 @@ question: ポインタとは、変数の「値」ではなく、その変数がメモリ上の**どこにあるか(アドレス)**を格納する変数です。 -[[変数]]の型に応じて、対応するポインタの型が存在します。例えば、`int`型の変数のアドレスを格納するなら `int*` 型、`double`型の変数のアドレスを格納するなら `double*` 型のポインタを使います。アスタリスク `*` がポインタ型であることを示します。 +[[変数]]の型に応じて、対応するポインタの型が存在します。例えば、[[`int`]]型の変数のアドレスを格納するなら `int*` 型、[[`double`]]型の変数のアドレスを格納するなら `double*` 型のポインタを使います。アスタリスク `*` がポインタ型であることを示します。 > ポインタ変数の宣言時に `*` を型の横に付けるか、変数名の横に付けるかは好みが分かれますが、意味は同じです (`int* p;` と `int *p;` は等価)。このチュートリアルでは `int* p;` のように型の側に付けます。 diff --git a/public/docs/cpp/3-pointers/2-0-array.md b/public/docs/cpp/3-pointers/2-0-array.md index e5f5f546..c051f63a 100644 --- a/public/docs/cpp/3-pointers/2-0-array.md +++ b/public/docs/cpp/3-pointers/2-0-array.md @@ -14,7 +14,7 @@ question: [[./2]]では `std::vector` を使いましたが、C++にはC言語互換の「生の配列(Cスタイル配列)」も存在します。これはサイズが固定で、機能が制限されています。 * **配列名の減衰(Decay):** 配列の名前は式の中で使うと、**「先頭要素へのポインタ」**として扱われます。これを「減衰(Decay)」と呼びます。 -* **ポインタ演算:** ポインタに対して数値を足し引きすると、**「その型のサイズ分」**だけアドレスが移動します。`int`(通常4バイト)のポインタに `+1` すると、メモリアドレスは4増えます。 +* **ポインタ演算:** ポインタに対して数値を足し引きすると、**「その型のサイズ分」**だけアドレスが移動します。[[`int`]](通常4バイト)のポインタに `+1` すると、メモリアドレスは4増えます。 ```cpp:array_decay.cpp #include diff --git a/public/docs/cpp/3-pointers/3-0-legacy-string.md b/public/docs/cpp/3-pointers/3-0-legacy-string.md index c12c4c34..bec6e966 100644 --- a/public/docs/cpp/3-pointers/3-0-legacy-string.md +++ b/public/docs/cpp/3-pointers/3-0-legacy-string.md @@ -10,7 +10,7 @@ question: ## 文字列リテラルと `char*` -`std::string` が登場する前、文字列は単なる `char` 型の配列でした。これを「Cスタイル文字列」と呼びます。 +`std::string` が登場する前、文字列は単なる [[`char`]] 型の配列でした。これを「Cスタイル文字列」と呼びます。 現在でも、ライブラリとの連携などで頻繁に目にします。 Cスタイル文字列は、文字の並びの最後に「終端文字 `\0`(ヌル文字)」を置くことで終わりを表します。 diff --git a/public/docs/cpp/3-pointers/5-1-practice1.md b/public/docs/cpp/3-pointers/5-1-practice1.md index 5554b5db..594b5ed6 100644 --- a/public/docs/cpp/3-pointers/5-1-practice1.md +++ b/public/docs/cpp/3-pointers/5-1-practice1.md @@ -9,7 +9,7 @@ question: ### 練習問題1: ポインタによる配列操作 -`int` 型のCスタイル配列 `arr` について、 `int*` 型のポインタを使って走査し、**すべての値を2倍に書き換えてください**(`[]` 演算子は使わず、ポインタ演算 `*` と `++` または `+` を使用すること)。 +[[`int`]] 型のCスタイル配列 `arr` について、 `int*` 型のポインタを使って走査し、**すべての値を2倍に書き換えてください**(`[]` 演算子は使わず、ポインタ演算 `*` と `++` または `+` を使用すること)。 ```cpp:practice4_1.cpp #include diff --git a/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md b/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md index 2c468721..400d9f89 100644 --- a/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md +++ b/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md @@ -45,6 +45,6 @@ Message: This is a potentially very large string... > **ガイドライン:** > -> * `int` や `double` などの基本型 → **値渡し** でOK。 +> * `int` や `double` などの[[基本型]] → **値渡し** でOK。 > * 変更させたいデータ → **参照渡し** (`T&`)。 > * 変更しないがサイズが大きいデータ(string, vectorなど) → **const参照渡し** (`const T&`)。 diff --git a/public/docs/cpp/7-classes-advanced/5-1-practice1.md b/public/docs/cpp/7-classes-advanced/5-1-practice1.md index f518ab38..22e445ce 100644 --- a/public/docs/cpp/7-classes-advanced/5-1-practice1.md +++ b/public/docs/cpp/7-classes-advanced/5-1-practice1.md @@ -9,7 +9,7 @@ question: ### 練習問題1: 複素数クラス -実部 (real) と虚部 (imaginary) を`double`型で持つ複素数クラス `Complex` を作成してください。以下の要件を満たすものとします。 +実部 (real) と虚部 (imaginary) を[[`double`]]型で持つ複素数クラス `Complex` を作成してください。以下の要件を満たすものとします。 1. コンストラクタで実部と虚部を初期化できるようにする。 2. 複素数同士の足し算 (`+`) と掛け算 (`*`) を演算子オーバーロードで実装する。 From a6df76b7c4add86010b055b0c2c66359af00dabb Mon Sep 17 00:00:00 2001 From: na-trium-144 <100704180+na-trium-144@users.noreply.github.com> Date: Sat, 8 Aug 2026 23:48:04 +0900 Subject: [PATCH 3/9] c++ 2 --- .../docs/cpp/1-types-control/1-0-basic-types.md | 2 +- public/docs/cpp/10-stl-containers/1-0-about.md | 2 +- public/docs/cpp/10-stl-containers/2-0-vector.md | 2 +- public/docs/cpp/10-stl-containers/4-0-other.md | 2 +- .../docs/cpp/10-stl-containers/5-2-practice2.md | 2 +- public/docs/cpp/11-stl-algorithms/1-0-about.md | 12 +++++++----- .../docs/cpp/11-stl-algorithms/4-1-practice1.md | 2 +- public/docs/cpp/2-data-containers/1-0-string.md | 8 +++++--- public/docs/cpp/2-data-containers/2-0-vector.md | 3 +++ public/docs/cpp/2-data-containers/3-0-array.md | 9 ++++++--- .../cpp/2-data-containers/4-0-range-based-for.md | 16 ++++++++++------ public/docs/cpp/2-data-containers/5-0-summary.md | 8 ++++---- .../docs/cpp/2-data-containers/5-1-practice1.md | 2 +- .../docs/cpp/2-data-containers/5-2-practice2.md | 4 +++- public/docs/cpp/3-pointers/-intro.md | 2 +- public/docs/cpp/3-pointers/2-0-array.md | 2 +- public/docs/cpp/3-pointers/3-0-legacy-string.md | 6 ++++-- public/docs/cpp/3-pointers/4-4-memory-leak.md | 8 +++++--- .../4-functions/2-4-arg-by-const-reference.md | 4 ++-- public/docs/cpp/9-templates/3-1-practice1.md | 2 +- public/docs/cpp/9-templates/3-2-practice2.md | 2 +- 21 files changed, 60 insertions(+), 40 deletions(-) diff --git a/public/docs/cpp/1-types-control/1-0-basic-types.md b/public/docs/cpp/1-types-control/1-0-basic-types.md index ede7093a..4f222bad 100644 --- a/public/docs/cpp/1-types-control/1-0-basic-types.md +++ b/public/docs/cpp/1-types-control/1-0-basic-types.md @@ -28,7 +28,7 @@ C++には多くの型がありますが、まずは以下の基本型を押さ * **整数型**: `int` (通常4バイト), `long long` (8バイト, 大きな整数) * **浮動小数点型**: `double` (倍精度, 基本的にこれを使う), `float` (単精度) - * **文字型**: `char` (1バイト文字), `std::string` (文字列クラス。厳密には基本型ではありませんが、実用上必須) + * **文字型**: `char` (1バイト文字), `std::string` ([[文字列]]クラス。厳密には基本型ではありませんが、実用上必須) * **ブール型**: `bool` (`true` または `false`) C++では[[変数]]のサイズ(ビット幅)が環境によって異なる場合がありますが、現代的な環境では `int` は32bit以上であることが保証されています。 diff --git a/public/docs/cpp/10-stl-containers/1-0-about.md b/public/docs/cpp/10-stl-containers/1-0-about.md index 9f641611..7985b97f 100644 --- a/public/docs/cpp/10-stl-containers/1-0-about.md +++ b/public/docs/cpp/10-stl-containers/1-0-about.md @@ -11,7 +11,7 @@ question: STLは、主に3つの要素から構成されています。 -1. **コンテナ (Containers)**: データを格納するためのデータ構造です。`vector`(可変長配列)や`map`(連想配列)など、様々な種類があります。 +1. **コンテナ (Containers)**: データを格納するためのデータ構造です。[[`std::vector`]](可変長配列)や`std::map`(連想配列)など、様々な種類があります。 2. **アルゴリズム (Algorithms)**: ソート、検索、変換など、コンテナ上のデータに対して操作を行う関数群です。 3. **イテレータ (Iterators)**: コンテナの要素を指し示し、アルゴリズムがコンテナの種類に依存せずに各要素にアクセスするための統一的なインターフェースを提供します。ポインタを一般化したようなものです。 diff --git a/public/docs/cpp/10-stl-containers/2-0-vector.md b/public/docs/cpp/10-stl-containers/2-0-vector.md index 9ad608b8..cc4c820b 100644 --- a/public/docs/cpp/10-stl-containers/2-0-vector.md +++ b/public/docs/cpp/10-stl-containers/2-0-vector.md @@ -12,7 +12,7 @@ question: ## `std::vector`: 最もよく使う可変長配列 -`std::vector`は、最も基本的で最もよく使われるコンテナです。他の言語でいうところの「リスト」や「動的配列」に相当し、要素を連続したメモリ領域に格納します。 +[[`std::vector`]]は、最も基本的で最もよく使われるコンテナです。他の言語でいうところの「リスト」や「動的配列」に相当し、要素を連続したメモリ領域に格納します。 **主な特徴**: diff --git a/public/docs/cpp/10-stl-containers/4-0-other.md b/public/docs/cpp/10-stl-containers/4-0-other.md index 3a2598e6..687ae098 100644 --- a/public/docs/cpp/10-stl-containers/4-0-other.md +++ b/public/docs/cpp/10-stl-containers/4-0-other.md @@ -19,4 +19,4 @@ STLには、他にも特定の目的に特化したコンテナが多数用意 * `std::unordered_map`: `std::map`と同様にキーと値のペアを管理しますが、内部的にハッシュテーブルを使うため、平均的な検索・挿入・削除がさらに高速 (`O(1)`) です。ただし、要素はソートされません。``ヘッダが必要です。 * `std::queue`, `std::stack`: それぞれ先入れ先出し (FIFO)、後入れ先出し (LIFO) のデータ構造を実装するためのコンテナアダプタです。 -どのコンテナを選択するかは、プログラムの要件(データのアクセスパターン、挿入・削除の頻度など)によって決まります。まずは`std::vector`を基本とし、必要に応じて他のコンテナを検討するのが良いアプローチです。 +どのコンテナを選択するかは、プログラムの要件(データのアクセスパターン、挿入・削除の頻度など)によって決まります。まずは[[`std::vector`]]を基本とし、必要に応じて他のコンテナを検討するのが良いアプローチです。 diff --git a/public/docs/cpp/10-stl-containers/5-2-practice2.md b/public/docs/cpp/10-stl-containers/5-2-practice2.md index cd92a0f8..b03fee27 100644 --- a/public/docs/cpp/10-stl-containers/5-2-practice2.md +++ b/public/docs/cpp/10-stl-containers/5-2-practice2.md @@ -14,7 +14,7 @@ question: 英文(スペースで区切られた単語の列)を読み込み、各単語が何回出現したかをカウントするプログラムを`std::map`を使って作成してください。最後に、出現した全単語とその出現回数をアルファベット順に表示してください。 -> 文字列を単語ごとに分割するには、以下のように`std::istringstream`を使うと便利です。 +> [[文字列]]を単語ごとに分割するには、以下のように`std::istringstream`を使うと便利です。 ```cpp #include diff --git a/public/docs/cpp/11-stl-algorithms/1-0-about.md b/public/docs/cpp/11-stl-algorithms/1-0-about.md index d2b25f13..7cba2a9d 100644 --- a/public/docs/cpp/11-stl-algorithms/1-0-about.md +++ b/public/docs/cpp/11-stl-algorithms/1-0-about.md @@ -14,7 +14,7 @@ question: ## イテレータ:コンテナとアルゴリズムを繋ぐ架け橋 -アルゴリズムは、特定のコンテナ(`std::vector` や `std::list` など)に直接依存しないように設計されています。では、どうやってコンテナ内の要素にアクセスするのでしょうか?そこで登場するのが**イテレータ (Iterator)** です。 +アルゴリズムは、特定のコンテナ([[`std::vector`]] や `std::list` など)に直接依存しないように設計されています。では、どうやってコンテナ内の要素にアクセスするのでしょうか?そこで登場するのが**イテレータ (Iterator)** です。 イテレータは、コンテナ内の要素を指し示す「ポインタのような」オブジェクトです。ポインタのように `*` で要素の値を参照したり、`++` で次の要素に進んだりできます。 @@ -25,7 +25,11 @@ question: アルゴリズムは、この `begin()` と `end()` から得られるイテレータのペアを使い、操作対象の「範囲」を指定します。範囲は半開区間 `[begin, end)` で表され、`begin` が指す要素は範囲に含まれ、`end` が指す要素は含まれません。 -簡単な例を見てみましょう。イテレータを使って `vector` の全要素を表示するコードです。 +> [!TIP] +> [[範囲ベース for ループ]] では内部でイテレータが使われており、 [[`std::vector`]] などに限らずイテレータが取得できるオブジェクトに対して使用できます。 + +簡単な例を見てみましょう。イテレータを使って [[`std::vector`]] の全要素を表示するコードです。 +このように、イテレータはコンテナの種類を問わず、統一的な方法で要素にアクセスする仕組みを提供します。これが、アルゴリズムが様々なコンテナに対して汎用的に機能する理由です。 ```cpp:iterator_example.cpp #include @@ -41,7 +45,7 @@ int main() { } std::cout << std::endl; - // C++11以降の範囲ベースforループ (内部ではイテレータが使われている) + // C++11以降の範囲ベースforループ std::cout << "Numbers (range-based for): "; for (int num : numbers) { std::cout << num << " "; @@ -56,5 +60,3 @@ int main() { Numbers: 0 1 2 3 4 Numbers (range-based for): 0 1 2 3 4 ``` - -このように、イテレータはコンテナの種類を問わず、統一的な方法で要素にアクセスする仕組みを提供します。これが、アルゴリズムが様々なコンテナに対して汎用的に機能する理由です。 diff --git a/public/docs/cpp/11-stl-algorithms/4-1-practice1.md b/public/docs/cpp/11-stl-algorithms/4-1-practice1.md index d7ea52d1..600986ff 100644 --- a/public/docs/cpp/11-stl-algorithms/4-1-practice1.md +++ b/public/docs/cpp/11-stl-algorithms/4-1-practice1.md @@ -10,7 +10,7 @@ question: ### 練習問題1: 文字列の長さでソート -`std::vector` を用意し、格納されている文字列を、文字数が短い順にソートして、結果を出力するプログラムを作成してください。`std::sort` とラムダ式を使用してください。 +`std::vector` を用意し、格納されている[[文字列]]を、文字数が短い順にソートして、結果を出力するプログラムを作成してください。`std::sort` とラムダ式を使用してください。 **ヒント**: ラムダ式は2つの文字列を引数に取り、1つ目の文字列の長さが2つ目の文字列の長さより短い場合に `true` を返すように実装します。 diff --git a/public/docs/cpp/2-data-containers/1-0-string.md b/public/docs/cpp/2-data-containers/1-0-string.md index 0d687ef7..0bf6f114 100644 --- a/public/docs/cpp/2-data-containers/1-0-string.md +++ b/public/docs/cpp/2-data-containers/1-0-string.md @@ -8,6 +8,9 @@ question: - 文字列を結合する際に、+演算子をたくさん使うとパフォーマンスに影響はありますか? - std::stringを使うためには必ず#include が必要ですか? - std::stringの.size()メソッドは、半角英数字以外の文字(日本語など)でも正しく文字数を数えられますか? +term: + - 文字列 + - std::string --- ## 文字列の扱い:`std::string` @@ -22,7 +25,8 @@ C++では、標準ライブラリの `std::string` クラスを使用します * **比較**: `==`, `!=` などで中身の文字列比較が可能(C言語の `strcmp` は不要)。 * **サイズ取得**: `.size()` または `.length()` メソッドを使用。 - +> [!NOTE] +> `std::string` は必要に応じて自動的にメモリを拡張します。プログラマがメモリ確保(malloc/free)を気にする必要はありません。 ```cpp:string_demo.cpp #include @@ -61,5 +65,3 @@ Length: 13 Greeting matches 'Hello'. Modified: hello, World! ``` - -> **Note:** `std::string` は必要に応じて自動的にメモリを拡張します。プログラマがメモリ確保(malloc/free)を気にする必要はありません。 diff --git a/public/docs/cpp/2-data-containers/2-0-vector.md b/public/docs/cpp/2-data-containers/2-0-vector.md index 10ed711d..a9b4bc24 100644 --- a/public/docs/cpp/2-data-containers/2-0-vector.md +++ b/public/docs/cpp/2-data-containers/2-0-vector.md @@ -8,6 +8,9 @@ question: - .push_back()以外に、std::vectorの途中に要素を追加する方法はありますか? - intやdouble以外の型、例えばstd::stringや自分で作ったクラスのオブジェクトも格納できますか? - C++11以前の環境では初期化リストを使えないとのことですが、その場合はどうやって初期化すればいいですか? +term: + - 可変長配列 + - std::vector --- ## 可変長配列:`std::vector` diff --git a/public/docs/cpp/2-data-containers/3-0-array.md b/public/docs/cpp/2-data-containers/3-0-array.md index fb89a931..8fd6a239 100644 --- a/public/docs/cpp/2-data-containers/3-0-array.md +++ b/public/docs/cpp/2-data-containers/3-0-array.md @@ -9,14 +9,17 @@ question: 3>の違いをもっと詳しく知りたいです。なぜstd::arrayの方が良いのですか? - std::arrayは宣言時にサイズが固定されますが、後からサイズを変更することはできませんか? - 「スタック確保」とありますが、スタックとは何ですか?ヒープとは違うのですか? +term: + - 固定長配列 + - std::array --- ## 固定長配列:`std::array` -データの個数が決まっている場合(例えば、3次元座標、RGB値、固定バッファなど)は、`std::vector` よりも `std::array` が適しています。 +データの個数が決まっている場合(例えば、3次元座標、RGB値、固定バッファなど)は、[[`std::vector`]] よりも `std::array` が適しています。 -「なぜ昔ながらの `int arr[5];` を使わないの?」と思われるかもしれません。 -Cスタイルの配列は、他のコンテナ(vectorなど)と操作感が異なり、サイズ情報を自分で管理しなければならないなどの欠点があります。`std::array` はC配列のパフォーマンス(スタック確保)と、コンテナの利便性(`.size()`などが使える)を両立させたものです。 +> [!NOTE] +> 固定長の配列として、Cスタイルの配列 (`int coords[3];` など) もあります。しかし、Cスタイルの配列は、他のコンテナ(vectorなど)と操作感が異なり、サイズ情報を自分で管理しなければならないなどの欠点があります。`std::array` はC配列のパフォーマンス(スタック確保)と、コンテナの利便性(`.size()`などが使える)を両立させたものです。 ```cpp:array_demo.cpp #include diff --git a/public/docs/cpp/2-data-containers/4-0-range-based-for.md b/public/docs/cpp/2-data-containers/4-0-range-based-for.md index dfff2c64..0b9dfbd2 100644 --- a/public/docs/cpp/2-data-containers/4-0-range-based-for.md +++ b/public/docs/cpp/2-data-containers/4-0-range-based-for.md @@ -8,11 +8,13 @@ question: - 「要素を『コピー』して取り出す」とは具体的にどういうことですか? - 「const auto& item」の「&」は何を意味するのですか?なぜコピーコストを避けられるのですか? - 従来のforループ (int i = 0; ...) と範囲ベースforループでは、パフォーマンスに違いはありますか? +term: + - 範囲ベース for ループ --- ## 範囲ベース `for` ループ (Range-based for) -`std::vector` や `std::array` の中身を順番に処理する場合、インデックス `i` を使った [[`for`]] 文 (`for (int i = 0; i < n; ++i)`) は書くのが面倒ですし、境界外アクセスのリスクがあります。 +[[`std::vector`]] や [[`std::array`]] の中身を順番に処理する場合、インデックス `i` を使った [[`for`]] 文 (`for (int i = 0; i < n; ++i)`) は書くのが面倒ですし、境界外アクセスのリスクがあります。 モダンC++では、PythonやC\#の `foreach` に相当する **範囲ベース for ループ** が使えます。 @@ -22,7 +24,13 @@ for (要素の型 変数名 : コンテナ) { } ``` -ここで便利なのが、**[[`auto`]] キーワード**です。`auto` を使うと、コンパイラが型を自動推論してくれるため、型名を詳しく書く必要がなくなります。 +> [!TIP] +> ここで便利なのが、**[[`auto`]] キーワード**です。`auto` を使うと、コンパイラが型を自動推論してくれるため、型名を詳しく書く必要がなくなります。 + + + +> [!WARNING] +> 以下のコードの `auto item` は、要素を「コピー」して取り出します。[[`std::string`]] のような大きなデータを扱う場合、コピーコストを避けるために `const auto& item` (参照)を使うのが一般的ですが、これについては[[./5]]で詳しく解説します。今の段階では「`auto` でループが回せる」と覚えておけば十分です。 ```cpp:range_for_demo.cpp #include @@ -60,7 +68,3 @@ int main() { - Potion Total Score: 307 ``` - -> **Advanced Hint:** -> 上記の `auto item` は、要素を「コピー」して取り出します。`std::string` のような大きなデータを扱う場合、コピーコストを避けるために `const auto& item` (参照)を使うのが一般的ですが、これについては[[./5]]で詳しく解説します。今の段階では「`auto` でループが回せる」と覚えておけば十分です。 - diff --git a/public/docs/cpp/2-data-containers/5-0-summary.md b/public/docs/cpp/2-data-containers/5-0-summary.md index 7efe3570..dc269ac9 100644 --- a/public/docs/cpp/2-data-containers/5-0-summary.md +++ b/public/docs/cpp/2-data-containers/5-0-summary.md @@ -7,9 +7,9 @@ question: [] ## この章のまとめ -1. **文字列**: `char*` ではなく `std::string` を使う。結合や比較が簡単で安全。 -2. **動的配列**: データの増減がある場合は `std::vector` を使う。`push_back()` で追加できる。 -3. **固定配列**: サイズ固定の場合は `std::array` を使う。Cスタイル配列のモダンな代替。 -4. **ループ**: コンテナの全要素走査には「範囲ベース for ループ」と [[`auto`]] を使うとシンプルに書ける。 +1. **文字列**: `char*` ではなく [[`std::string`]] を使う。結合や比較が簡単で安全。 +2. **動的配列**: データの増減がある場合は [[`std::vector`]] を使う。`push_back()` で追加できる。 +3. **固定配列**: サイズ固定の場合は [[`std::array`]] を使う。Cスタイル配列のモダンな代替。 +4. **ループ**: コンテナの全要素走査には「[[範囲ベース for ループ]]」と [[`auto`]] を使うとシンプルに書ける。 これらの「標準ライブラリ(STL: Standard Template Library)」のコンテナを活用することで、メモリ管理の苦労を飛ばして、アプリケーションのロジックに集中できるようになります。 diff --git a/public/docs/cpp/2-data-containers/5-1-practice1.md b/public/docs/cpp/2-data-containers/5-1-practice1.md index fd65b12b..60ce51f8 100644 --- a/public/docs/cpp/2-data-containers/5-1-practice1.md +++ b/public/docs/cpp/2-data-containers/5-1-practice1.md @@ -10,7 +10,7 @@ question: ### 練習問題1: 数値リストの統計 `std::vector` を使用して、好きな整数を5つほど格納してください(コード内で直接[[初期化]]して構いません)。 -その後、範囲ベース for ループを使用して、その数値の「合計」と「最大値」を求めて出力するプログラムを作成してください。 +その後、[[範囲ベース for ループ]]を使用して、その数値の「合計」と「最大値」を求めて出力するプログラムを作成してください。 ```cpp:practice3_1.cpp #include diff --git a/public/docs/cpp/2-data-containers/5-2-practice2.md b/public/docs/cpp/2-data-containers/5-2-practice2.md index 950c155f..81a038c9 100644 --- a/public/docs/cpp/2-data-containers/5-2-practice2.md +++ b/public/docs/cpp/2-data-containers/5-2-practice2.md @@ -9,7 +9,9 @@ question: ### 練習問題2: 単語のフィルタリング 以下の単語リスト `words` の中から、**文字数(長さ)が5文字より大きい単語だけ**を選んで表示するプログラムを作成してください。 -(ヒント:`std::string` の `.size()` または `.length()` メソッドと [[`if`]] 文を使用します) + +> [!TIP] +> [[`std::string`]] の `.size()` または `.length()` メソッドと [[`if`]] 文を使用します) ```cpp:practice3_2.cpp #include diff --git a/public/docs/cpp/3-pointers/-intro.md b/public/docs/cpp/3-pointers/-intro.md index 0bff3f21..685e1d61 100644 --- a/public/docs/cpp/3-pointers/-intro.md +++ b/public/docs/cpp/3-pointers/-intro.md @@ -1,5 +1,5 @@ ようこそ、C++学習の最大の山場へ。 -[[./2]]では、`std::vector`や`std::string`といった便利な機能を使ってきましたが、今回はその「裏側」で何が起きているかを覗き込みます。 +[[./2]]では、[[`std::vector`]]や[[`std::string`]]といった便利な機能を使ってきましたが、今回はその「裏側」で何が起きているかを覗き込みます。 他の言語(Java, Python, C\#など)では言語機能やガベージコレクション(GC)が隠蔽してくれている「メモリ」という物理的なリソースを、C++では直接操作することができます。これがC++の強力な武器であり、同時にバグの温床でもあります。 diff --git a/public/docs/cpp/3-pointers/2-0-array.md b/public/docs/cpp/3-pointers/2-0-array.md index c051f63a..d9749c3b 100644 --- a/public/docs/cpp/3-pointers/2-0-array.md +++ b/public/docs/cpp/3-pointers/2-0-array.md @@ -11,7 +11,7 @@ question: ## 配列とポインタの関係 -[[./2]]では `std::vector` を使いましたが、C++にはC言語互換の「生の配列(Cスタイル配列)」も存在します。これはサイズが固定で、機能が制限されています。 +[[./2]]では [[`std::vector`]] を使いましたが、C++にはC言語互換の「生の配列(Cスタイル配列)」も存在します。これはサイズが固定で、機能が制限されています。 * **配列名の減衰(Decay):** 配列の名前は式の中で使うと、**「先頭要素へのポインタ」**として扱われます。これを「減衰(Decay)」と呼びます。 * **ポインタ演算:** ポインタに対して数値を足し引きすると、**「その型のサイズ分」**だけアドレスが移動します。[[`int`]](通常4バイト)のポインタに `+1` すると、メモリアドレスは4増えます。 diff --git a/public/docs/cpp/3-pointers/3-0-legacy-string.md b/public/docs/cpp/3-pointers/3-0-legacy-string.md index bec6e966..85585679 100644 --- a/public/docs/cpp/3-pointers/3-0-legacy-string.md +++ b/public/docs/cpp/3-pointers/3-0-legacy-string.md @@ -10,11 +10,14 @@ question: ## 文字列リテラルと `char*` -`std::string` が登場する前、文字列は単なる [[`char`]] 型の配列でした。これを「Cスタイル文字列」と呼びます。 +[[`std::string`]] が登場する前、文字列は単なる [[`char`]] 型の配列でした。これを「Cスタイル文字列」と呼びます。 現在でも、ライブラリとの連携などで頻繁に目にします。 Cスタイル文字列は、文字の並びの最後に「終端文字 `\0`(ヌル文字)」を置くことで終わりを表します。 +> [!IMPORTANT] +> モダンC++では基本的に [[`std::string`]] を使いましょう。`char*` は参照用やAPI互換のために使います。 + ```cpp:legacy_string.cpp #include #include @@ -44,4 +47,3 @@ C++ String: World Converted to C-Style: World ``` -**重要:** モダンC++では基本的に `std::string` を使いましょう。`char*` は参照用やAPI互換のために使います。 diff --git a/public/docs/cpp/3-pointers/4-4-memory-leak.md b/public/docs/cpp/3-pointers/4-4-memory-leak.md index 52e9b1c6..63f4bbb6 100644 --- a/public/docs/cpp/3-pointers/4-4-memory-leak.md +++ b/public/docs/cpp/3-pointers/4-4-memory-leak.md @@ -14,9 +14,11 @@ question: もし `delete` を忘れるとどうなるでしょう? 確保されたメモリは、プログラムが終了するまで「使用中」のまま残ります。これを**メモリリーク**と呼びます。長時間動くサーバーなどでこれが起きると、メモリを食いつぶしてシステムがクラッシュします。 -**[[./2]]の振り返り:** -`std::vector` や `std::string` は、内部で `new` と `delete` を自動的に行ってくれています。 +> [!TIP] +> **[[./2]]の振り返り:** +> [[`std::vector`]] や [[`std::string`]] は、内部で `new` と `delete` を自動的に行ってくれています。 * 作成時に `new` で確保。 * スコープを抜けるときに自動で `delete`(デストラクタ)。 - これがC++のクラスの強力な機能(RAII)です。生の `new/delete` を直接使うことは、モダンC++では「最後の手段」あるいは「ライブラリを作る側の仕事」と考えられています。 + +これがC++のクラスの強力な機能(RAII)です。生の `new/delete` を直接使うことは、モダンC++では「最後の手段」あるいは「ライブラリを作る側の仕事」と考えられています。 diff --git a/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md b/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md index 400d9f89..eb867b3e 100644 --- a/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md +++ b/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md @@ -13,7 +13,7 @@ question: これが**C++で最も頻繁に使われるパターン**です。「コピーはしたくない(重いから)。でも、関数内で書き換えられたくもない」という要求を満たします。 * **構文:** `const 型& 引数名` - * **用途:** `std::string`、`std::vector`、クラスのオブジェクトなど、サイズが大きくなる可能性があるデータ。 + * **用途:** [[`std::string`]]、[[`std::vector`]]、クラスのオブジェクトなど、サイズが大きくなる可能性があるデータ。 @@ -47,4 +47,4 @@ Message: This is a potentially very large string... > > * `int` や `double` などの[[基本型]] → **値渡し** でOK。 > * 変更させたいデータ → **参照渡し** (`T&`)。 -> * 変更しないがサイズが大きいデータ(string, vectorなど) → **const参照渡し** (`const T&`)。 +> * 変更しないがサイズが大きいデータ([[`std::string`]], [[`std::vector`]]など) → **const参照渡し** (`const T&`)。 diff --git a/public/docs/cpp/9-templates/3-1-practice1.md b/public/docs/cpp/9-templates/3-1-practice1.md index a4d6e0fa..21179348 100644 --- a/public/docs/cpp/9-templates/3-1-practice1.md +++ b/public/docs/cpp/9-templates/3-1-practice1.md @@ -12,7 +12,7 @@ question: ### 練習問題1: 汎用的なprint関数 -任意の型の配列(ここでは`std::vector`を使いましょう)を受け取り、その要素をすべて画面に出力する関数テンプレート`print_elements`を作成してください。 +任意の型の配列(ここでは[[`std::vector`]]を使いましょう)を受け取り、その要素をすべて画面に出力する関数テンプレート`print_elements`を作成してください。 ```cpp:practice10_1.cpp #include diff --git a/public/docs/cpp/9-templates/3-2-practice2.md b/public/docs/cpp/9-templates/3-2-practice2.md index 5435ec91..bc524992 100644 --- a/public/docs/cpp/9-templates/3-2-practice2.md +++ b/public/docs/cpp/9-templates/3-2-practice2.md @@ -18,7 +18,7 @@ question: * `T pop()`: スタックの先頭から要素を取り出す * `bool is_empty()`: スタックが空かどうかを返す -`std::vector`を内部のデータ格納場所として利用して構いません。`int`型と`char`型で動作を確認してください。 +[[`std::vector`]]を内部のデータ格納場所として利用して構いません。`int`型と`char`型で動作を確認してください。 ```cpp:practice10_2.cpp #include From 34f4e48300ecdfcb920ab95b2075f073d9560f92 Mon Sep 17 00:00:00 2001 From: na-trium-144 <100704180+na-trium-144@users.noreply.github.com> Date: Sun, 9 Aug 2026 15:17:40 +0900 Subject: [PATCH 4/9] c++ 3 --- public/docs/cpp/10-stl-containers/1-0-about.md | 2 +- public/docs/cpp/11-stl-algorithms/1-0-about.md | 2 +- public/docs/cpp/12-raii-smart-ptrs/-intro.md | 2 +- public/docs/cpp/12-raii-smart-ptrs/1-1-leak.md | 4 ++-- public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md | 2 +- public/docs/cpp/12-raii-smart-ptrs/3-0-smartptr.md | 4 ++-- public/docs/cpp/12-raii-smart-ptrs/3-2-sharedptr.md | 2 +- public/docs/cpp/12-raii-smart-ptrs/4-0-summary.md | 4 ++-- public/docs/cpp/2-data-containers/-intro.md | 2 +- public/docs/cpp/2-data-containers/1-0-string.md | 2 +- public/docs/cpp/2-data-containers/3-0-array.md | 2 +- public/docs/cpp/2-data-containers/5-0-summary.md | 2 +- public/docs/cpp/3-pointers/1-0-basic.md | 4 ++++ public/docs/cpp/3-pointers/1-1-address-operator.md | 7 ++++--- public/docs/cpp/3-pointers/1-2-nullptr.md | 6 ++++-- public/docs/cpp/3-pointers/2-0-array.md | 10 +++++++--- public/docs/cpp/3-pointers/3-0-legacy-string.md | 7 ++++++- public/docs/cpp/3-pointers/4-1-stack.md | 2 ++ public/docs/cpp/3-pointers/4-2-heap.md | 4 ++++ public/docs/cpp/3-pointers/4-4-memory-leak.md | 10 ++++++---- public/docs/cpp/3-pointers/5-0-summary.md | 8 ++++---- public/docs/cpp/3-pointers/5-1-practice1.md | 2 +- public/docs/cpp/3-pointers/5-2-practice2.md | 2 +- public/docs/cpp/4-functions/-intro.md | 2 +- public/docs/cpp/4-functions/2-2-arg-by-pointer.md | 6 +++--- public/docs/cpp/4-functions/2-3-arg-by-reference.md | 2 +- public/docs/cpp/4-functions/4-0-summary.md | 2 +- public/docs/cpp/4-functions/4-1-practice1.md | 2 +- public/docs/cpp/7-classes-advanced/1-0-copy.md | 2 +- public/docs/cpp/7-classes-advanced/1-1-shallow-copy.md | 4 ++-- public/docs/cpp/7-classes-advanced/1-2-deep-copy.md | 6 +++--- public/docs/cpp/7-classes-advanced/4-0-this.md | 6 +++--- public/docs/cpp/7-classes-advanced/5-0-summary.md | 4 ++-- public/docs/cpp/7-classes-advanced/5-2-practice2.md | 2 +- public/docs/cpp/8-inheritance/2-0-polymorphism.md | 4 ++-- public/docs/cpp/8-inheritance/5-0-summary.md | 2 +- public/docs/cpp/8-inheritance/5-1-practice1.md | 2 +- 37 files changed, 81 insertions(+), 57 deletions(-) diff --git a/public/docs/cpp/10-stl-containers/1-0-about.md b/public/docs/cpp/10-stl-containers/1-0-about.md index 7985b97f..01efff1f 100644 --- a/public/docs/cpp/10-stl-containers/1-0-about.md +++ b/public/docs/cpp/10-stl-containers/1-0-about.md @@ -13,6 +13,6 @@ STLは、主に3つの要素から構成されています。 1. **コンテナ (Containers)**: データを格納するためのデータ構造です。[[`std::vector`]](可変長配列)や`std::map`(連想配列)など、様々な種類があります。 2. **アルゴリズム (Algorithms)**: ソート、検索、変換など、コンテナ上のデータに対して操作を行う関数群です。 -3. **イテレータ (Iterators)**: コンテナの要素を指し示し、アルゴリズムがコンテナの種類に依存せずに各要素にアクセスするための統一的なインターフェースを提供します。ポインタを一般化したようなものです。 +3. **イテレータ (Iterators)**: コンテナの要素を指し示し、アルゴリズムがコンテナの種類に依存せずに各要素にアクセスするための統一的なインターフェースを提供します。[[ポインタ]]を一般化したようなものです。 これら3つが連携することで、C++プログラマは効率的で再利用性の高いコードを素早く書くことができます。この章では「コンテナ」を、[[./11]]では「アルゴリズム」と、それらをつなぐ「イテレータ」の応用を詳しく見ていきます。 diff --git a/public/docs/cpp/11-stl-algorithms/1-0-about.md b/public/docs/cpp/11-stl-algorithms/1-0-about.md index 7cba2a9d..9a70c448 100644 --- a/public/docs/cpp/11-stl-algorithms/1-0-about.md +++ b/public/docs/cpp/11-stl-algorithms/1-0-about.md @@ -16,7 +16,7 @@ question: アルゴリズムは、特定のコンテナ([[`std::vector`]] や `std::list` など)に直接依存しないように設計されています。では、どうやってコンテナ内の要素にアクセスするのでしょうか?そこで登場するのが**イテレータ (Iterator)** です。 -イテレータは、コンテナ内の要素を指し示す「ポインタのような」オブジェクトです。ポインタのように `*` で要素の値を参照したり、`++` で次の要素に進んだりできます。 +イテレータは、コンテナ内の要素を指し示す「[[ポインタ]]のような」オブジェクトです。[[ポインタ]]のように `*` で要素の値を参照したり、`++` で次の要素に進んだりできます。 ほとんどのコンテナは、以下の2つの重要なイテレータを取得するメンバ関数を持っています。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/-intro.md b/public/docs/cpp/12-raii-smart-ptrs/-intro.md index d0f49220..a3b29f71 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/-intro.md +++ b/public/docs/cpp/12-raii-smart-ptrs/-intro.md @@ -1,3 +1,3 @@ -[[./3]]で、`new` と `delete` を使った動的なメモリ管理を学びました。しかし、これらの手動管理は `delete` の呼び忘れによるメモリリークや、複雑なコードでのリソース管理の煩雑さを引き起こす原因となりがちです。 +[[./3]]で、[[`new`]] と [[`delete`]] を使った動的なメモリ管理を学びました。しかし、これらの手動管理は `delete` の呼び忘れによるメモリリークや、複雑なコードでのリソース管理の煩雑さを引き起こす原因となりがちです。 C++11以降の「モダンC++」では、こうした問題を解決するための洗練された仕組みが導入されました。この章では、エラーハンドリングのための**例外処理**、リソース管理の基本思想である **RAIIイディオム**、そしてそれを具現化する**スマートポインタ** (`std::unique_ptr`, `std::shared_ptr`) について学び、より安全で堅牢なコードを書くための流儀を身につけます。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/1-1-leak.md b/public/docs/cpp/12-raii-smart-ptrs/1-1-leak.md index d34991c1..679ad666 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/1-1-leak.md +++ b/public/docs/cpp/12-raii-smart-ptrs/1-1-leak.md @@ -11,7 +11,7 @@ question: ### 例外とリソースリーク -ここで、`new` と `delete` を使った手動のメモリ管理と例外処理が組み合わさると、問題が発生します。 +ここで、[[`new`]] と [[`delete`]] を使った手動のメモリ管理と例外処理が組み合わさると、問題が発生します。 ```cpp:raw_pointer_problem.cpp #include @@ -48,6 +48,6 @@ Data allocated. Error: Something went wrong during processing! ``` -この例では、`process_data` 関数内で `throw` が実行されると、関数の実行が中断され `catch` ブロックにジャンプします。その結果、`delete[] data;` の行が実行されず、確保されたメモリが解放されない**メモリリーク**が発生します。 +この例では、`process_data` 関数内で `throw` が実行されると、関数の実行が中断され `catch` ブロックにジャンプします。その結果、`delete[] data;` の行が実行されず、確保されたメモリが解放されない**[[メモリリーク]]**が発生します。 この問題を解決するのが、C++の最も重要な設計思想の一つである **RAII** です。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md b/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md index 4a650000..87b9c8f1 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md +++ b/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md @@ -16,7 +16,7 @@ question: C++では、オブジェクトがそのスコープ([[変数]]が宣言された `{}` の範囲)を抜けるときに、そのオブジェクトの**デストラクタ**が自動的に呼び出されます。この仕組みは、関数が正常に終了した場合だけでなく、**例外が投げられてスコープを抜ける場合でも保証されています**。 -RAIIはこの性質を利用して、リソースの解放処理をデストラクタに記述することで、リソースの解放を自動化し、`delete` の呼び忘れや例外発生時のリソースリークを防ぎます。 +RAIIはこの性質を利用して、リソースの解放処理をデストラクタに記述することで、リソースの解放を自動化し、[[`delete`]] の呼び忘れや例外発生時のリソースリークを防ぎます。 簡単なRAIIクラスの例を見てみましょう。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/3-0-smartptr.md b/public/docs/cpp/12-raii-smart-ptrs/3-0-smartptr.md index 631896e0..0e2f962a 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/3-0-smartptr.md +++ b/public/docs/cpp/12-raii-smart-ptrs/3-0-smartptr.md @@ -10,6 +10,6 @@ question: ## スマートポインタ: new/deleteを自動化する -スマートポインタは、RAIIを実装したクラステンプレートで、生ポインタ (`int*` など) のように振る舞いながら、リソース (確保したメモリ) の所有権を管理し、適切なタイミングで自動的に解放してくれます。 +スマートポインタは、RAIIを実装したクラステンプレートで、生[[ポインタ]] (`int*` など) のように振る舞いながら、リソース (確保したメモリ) の所有権を管理し、適切なタイミングで自動的に解放してくれます。 -モダンC++では、メモリ管理に生ポインタを直接使うことはほとんどなく、スマートポインタを使うのが基本です。主に2種類のスマートポインタを使い分けます。 +モダンC++では、メモリ管理に生[[ポインタ]]を直接使うことはほとんどなく、スマートポインタを使うのが基本です。主に2種類のスマートポインタを使い分けます。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/3-2-sharedptr.md b/public/docs/cpp/12-raii-smart-ptrs/3-2-sharedptr.md index 8c5986a1..b42d6093 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/3-2-sharedptr.md +++ b/public/docs/cpp/12-raii-smart-ptrs/3-2-sharedptr.md @@ -16,7 +16,7 @@ question: `std::shared_ptr` は、管理するオブジェクトの**所有権を複数のポインタで共有できる**スマートポインタです。 * **共有された所有権**: `shared_ptr` は自由にコピーできます。コピーされるたびに、内部の**参照カウンタ**が増加します。 - * **自動解放**: `shared_ptr` が破棄される(デストラクタが呼ばれる)と参照カウンタが減少し、**参照カウンタが0になったとき**に、管理しているオブジェクトが解放(`delete`)されます。 + * **自動解放**: `shared_ptr` が破棄される(デストラクタが呼ばれる)と参照カウンタが減少し、**参照カウンタが0になったとき**に、管理しているオブジェクトが解放([[`delete`]])されます。 * **オーバーヘッド**: 参照カウンタを管理するための追加のメモリと処理が必要なため、`unique_ptr` よりもわずかにオーバーヘッドが大きいです。 `shared_ptr` を作成するには、`std::make_shared` を使うのが効率的で安全です。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/4-0-summary.md b/public/docs/cpp/12-raii-smart-ptrs/4-0-summary.md index a137263a..6ad99463 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/4-0-summary.md +++ b/public/docs/cpp/12-raii-smart-ptrs/4-0-summary.md @@ -11,8 +11,8 @@ question: * **例外処理**は `try`, `catch`, `throw` を使い、エラーが発生してもプログラムを安全に継続させるための仕組みです。 * 手動のメモリ管理下で例外が発生すると、**リソースリーク**を引き起こす危険があります。 * **RAIIイディオム**は、リソースの確保をコンストラクタ、解放をデストラクタで行うことで、リソース管理を自動化するC++の重要な設計思想です。 - * **スマートポインタ**はRAIIを動的メモリ管理に適用したもので、`new` と `delete` の手動管理を不要にします。 + * **スマートポインタ**はRAIIを動的メモリ管理に適用したもので、[[`new`]] と [[`delete`]] の手動管理を不要にします。 * **`std::unique_ptr`** はオブジェクトの**唯一の所有権**を管理します。軽量であり、所有権が明確な場合に第一の選択肢となります。 * **`std::shared_ptr`** はオブジェクトの**所有権を共有**します。参照カウントによって管理され、最後の所有者がいなくなったときにオブジェクトを解放します。 -モダンC++プログラミングでは、`new` と `delete` を直接書くことは極力避け、RAIIとスマートポインタを全面的に活用することが、安全でメンテナンス性の高いコードへの第一歩です。 +モダンC++プログラミングでは、[[`new`]] と [[`delete`]] を直接書くことは極力避け、RAIIとスマートポインタを全面的に活用することが、安全でメンテナンス性の高いコードへの第一歩です。 diff --git a/public/docs/cpp/2-data-containers/-intro.md b/public/docs/cpp/2-data-containers/-intro.md index eebfba3f..a42fb7fb 100644 --- a/public/docs/cpp/2-data-containers/-intro.md +++ b/public/docs/cpp/2-data-containers/-intro.md @@ -1,3 +1,3 @@ -他の言語(Python, JavaScript, C\#など)経験者がC++を学び始めるとき、最も躓きやすいのが「文字や配列の扱い」です。古いC言語の教科書では、ポインタ操作やメモリ管理が必須となる「Cスタイル」のやり方から入ることが多いのですが、**現代の実務的なC++(モダンC++)では、もっと安全で便利な「クラス(コンテナ)」を使います。** +他の言語(Python, JavaScript, C\#など)経験者がC++を学び始めるとき、最も躓きやすいのが「文字や配列の扱い」です。古いC言語の教科書では、[[ポインタ]]操作やメモリ管理が必須となる「Cスタイル」のやり方から入ることが多いのですが、**現代の実務的なC++(モダンC++)では、もっと安全で便利な「クラス(コンテナ)」を使います。** この章では、ポインタの複雑な話を抜きにして、他の高級言語と同じくらい直感的にデータを扱えるツールを紹介します。 diff --git a/public/docs/cpp/2-data-containers/1-0-string.md b/public/docs/cpp/2-data-containers/1-0-string.md index 0bf6f114..a1cf041b 100644 --- a/public/docs/cpp/2-data-containers/1-0-string.md +++ b/public/docs/cpp/2-data-containers/1-0-string.md @@ -15,7 +15,7 @@ term: ## 文字列の扱い:`std::string` -C言語では文字列を扱うために `char*` や `char[]` を使い、ヌル終端文字 `\0` を意識する必要がありました。これはバグの温床です。 +C言語では文字列を扱うために [[`char*`]] や `char[]` を使い、ヌル終端文字 `\0` を意識する必要がありました。これはバグの温床です。 C++では、標準ライブラリの `std::string` クラスを使用します。これはPythonの `str` や Javaの `String` のように直感的に扱えます。 **主な機能** diff --git a/public/docs/cpp/2-data-containers/3-0-array.md b/public/docs/cpp/2-data-containers/3-0-array.md index 8fd6a239..24fce885 100644 --- a/public/docs/cpp/2-data-containers/3-0-array.md +++ b/public/docs/cpp/2-data-containers/3-0-array.md @@ -19,7 +19,7 @@ term: データの個数が決まっている場合(例えば、3次元座標、RGB値、固定バッファなど)は、[[`std::vector`]] よりも `std::array` が適しています。 > [!NOTE] -> 固定長の配列として、Cスタイルの配列 (`int coords[3];` など) もあります。しかし、Cスタイルの配列は、他のコンテナ(vectorなど)と操作感が異なり、サイズ情報を自分で管理しなければならないなどの欠点があります。`std::array` はC配列のパフォーマンス(スタック確保)と、コンテナの利便性(`.size()`などが使える)を両立させたものです。 +> 固定長の配列として、[[Cスタイルの配列]] (`int coords[3];` など) もあります。しかし、Cスタイルの配列は、他のコンテナ(vectorなど)と操作感が異なり、サイズ情報を自分で管理しなければならないなどの欠点があります。`std::array` はC配列のパフォーマンス([[スタック]]確保)と、コンテナの利便性(`.size()`などが使える)を両立させたものです。 ```cpp:array_demo.cpp #include diff --git a/public/docs/cpp/2-data-containers/5-0-summary.md b/public/docs/cpp/2-data-containers/5-0-summary.md index dc269ac9..73c74dcc 100644 --- a/public/docs/cpp/2-data-containers/5-0-summary.md +++ b/public/docs/cpp/2-data-containers/5-0-summary.md @@ -7,7 +7,7 @@ question: [] ## この章のまとめ -1. **文字列**: `char*` ではなく [[`std::string`]] を使う。結合や比較が簡単で安全。 +1. **文字列**: [[`char*`]] ではなく [[`std::string`]] を使う。結合や比較が簡単で安全。 2. **動的配列**: データの増減がある場合は [[`std::vector`]] を使う。`push_back()` で追加できる。 3. **固定配列**: サイズ固定の場合は [[`std::array`]] を使う。Cスタイル配列のモダンな代替。 4. **ループ**: コンテナの全要素走査には「[[範囲ベース for ループ]]」と [[`auto`]] を使うとシンプルに書ける。 diff --git a/public/docs/cpp/3-pointers/1-0-basic.md b/public/docs/cpp/3-pointers/1-0-basic.md index aea22cce..edeca570 100644 --- a/public/docs/cpp/3-pointers/1-0-basic.md +++ b/public/docs/cpp/3-pointers/1-0-basic.md @@ -6,6 +6,9 @@ question: - ポインタは具体的にどのような場面で使うと便利なのか、例を挙げてほしい。 - ポインタを使うことでプログラムにどんなメリットがあるのか。 - ポインタ自体も変数とのことだが、ポインタ変数のアドレスはどうやって確認するのか。 +term: + - ポインタ + - アドレス --- ## ポインタの基礎 @@ -14,4 +17,5 @@ question: [[変数]]の型に応じて、対応するポインタの型が存在します。例えば、[[`int`]]型の変数のアドレスを格納するなら `int*` 型、[[`double`]]型の変数のアドレスを格納するなら `double*` 型のポインタを使います。アスタリスク `*` がポインタ型であることを示します。 +> [!INFO] > ポインタ変数の宣言時に `*` を型の横に付けるか、変数名の横に付けるかは好みが分かれますが、意味は同じです (`int* p;` と `int *p;` は等価)。このチュートリアルでは `int* p;` のように型の側に付けます。 diff --git a/public/docs/cpp/3-pointers/1-1-address-operator.md b/public/docs/cpp/3-pointers/1-1-address-operator.md index 0acf0aee..62696ca6 100644 --- a/public/docs/cpp/3-pointers/1-1-address-operator.md +++ b/public/docs/cpp/3-pointers/1-1-address-operator.md @@ -11,8 +11,8 @@ question: ### アドレスと間接参照 - * **アドレス演算子 `&`**: [[変数]]のメモリ上の住所(アドレス)を取得します。 - * **間接参照演算子 `*`**: ポインタが指し示している住所に行き、その中身(値)にアクセスします。 + * **アドレス演算子 `&`**: [[変数]]のメモリ上の住所([[アドレス]])を取得します。 + * **間接参照演算子 `*`**: [[ポインタ]]が指し示している住所に行き、その中身(値)にアクセスします。 @@ -48,4 +48,5 @@ ptrが指す中身 (*ptr): 42 書き換え後のnumber: 100 ``` -※ アドレス(0x...)は実行環境ごとに異なります。 +> [!NOTE] +> アドレス(0x...)は実行環境ごとに異なります。 diff --git a/public/docs/cpp/3-pointers/1-2-nullptr.md b/public/docs/cpp/3-pointers/1-2-nullptr.md index 3e9f8e69..12e7127b 100644 --- a/public/docs/cpp/3-pointers/1-2-nullptr.md +++ b/public/docs/cpp/3-pointers/1-2-nullptr.md @@ -6,12 +6,14 @@ question: - 初期化されていないポインタが「不定な場所を指す」とは具体的にどういう意味か。何が危険なのか。 - '`nullptr`、`NULL`、`0` はどれも「何も指していない」ことを表すように見えるが、なぜモダンC++では`nullptr`を使うべきなのか。' - ポインタを`nullptr`で初期化した後、後から他の変数のアドレスを指すように変更できるのか。 +term: + - nullptr --- ### `nullptr` の使用 -ポインタが「どこも指していない」ことを示したい場合、C++では `nullptr` を使用します。 -古いC++やC言語では `NULL` や `0` が使われていましたが、モダンC++では型安全な `nullptr` を使うのが鉄則です。[[初期化]]されていないポインタは不定な場所を指すため、必ず初期化しましょう。 +[[ポインタ]]が「どこも指していない」ことを示したい場合、C++では `nullptr` を使用します。 +古いC++やC言語では `NULL` や `0` が使われていましたが、モダンC++では型安全な `nullptr` を使うのが鉄則です。[[初期化]]されていない[[ポインタ]]は不定な場所を指すため、必ず初期化しましょう。 ```cpp:pointer_declaration.cpp #include diff --git a/public/docs/cpp/3-pointers/2-0-array.md b/public/docs/cpp/3-pointers/2-0-array.md index d9749c3b..86b6b2af 100644 --- a/public/docs/cpp/3-pointers/2-0-array.md +++ b/public/docs/cpp/3-pointers/2-0-array.md @@ -7,14 +7,18 @@ question: - 「配列名の減衰」とは、いつどのように発生するのか。常に配列名がポインタになるのか。 - ポインタ演算で`+1`すると「その型のサイズ分」アドレスが移動するとのことだが、これは`int`以外の型でも同じなのか。 - '`*(ptr + 1)`のように括弧が必要なのはなぜか。`*ptr + 1`と書くとどうなるのか。' +term: + - Cスタイルの配列 + - Cスタイル配列 + - 生配列 --- ## 配列とポインタの関係 -[[./2]]では [[`std::vector`]] を使いましたが、C++にはC言語互換の「生の配列(Cスタイル配列)」も存在します。これはサイズが固定で、機能が制限されています。 +[[./2]]では [[`std::vector`]] や [[`std::array`]] を使いましたが、C++にはC言語互換の「生の配列(Cスタイル配列)」も存在します。これはサイズが固定で、機能が制限されています。 -* **配列名の減衰(Decay):** 配列の名前は式の中で使うと、**「先頭要素へのポインタ」**として扱われます。これを「減衰(Decay)」と呼びます。 -* **ポインタ演算:** ポインタに対して数値を足し引きすると、**「その型のサイズ分」**だけアドレスが移動します。[[`int`]](通常4バイト)のポインタに `+1` すると、メモリアドレスは4増えます。 +* **配列名の減衰(Decay):** 配列の名前は式の中で使うと、**「先頭要素への[[ポインタ]]」**として扱われます。これを「減衰(Decay)」と呼びます。 +* **ポインタ演算:** [[ポインタ]]に対して数値を足し引きすると、**「その型のサイズ分」**だけ[[アドレス]]が移動します。[[`int`]](通常4バイト)のポインタに `+1` すると、メモリアドレスは4増えます。 ```cpp:array_decay.cpp #include diff --git a/public/docs/cpp/3-pointers/3-0-legacy-string.md b/public/docs/cpp/3-pointers/3-0-legacy-string.md index 85585679..66046405 100644 --- a/public/docs/cpp/3-pointers/3-0-legacy-string.md +++ b/public/docs/cpp/3-pointers/3-0-legacy-string.md @@ -6,11 +6,16 @@ question: - '`const char* c_str = "Hello";` の`c_str`が指す文字列を変更することはできるのか。' - Cスタイル文字列の終端文字`\0`を忘れた場合、何が起こるのか。 - '`std::string`が推奨されるとのことだが、`char*`の知識は完全に不要になるのか。' +term: + - Cスタイルの文字列 + - Cスタイル文字列 + - char* + - char * --- ## 文字列リテラルと `char*` -[[`std::string`]] が登場する前、文字列は単なる [[`char`]] 型の配列でした。これを「Cスタイル文字列」と呼びます。 +[[`std::string`]] が登場する前、文字列は単なる [[`char`]] 型の生配列でした。これを「Cスタイル文字列」と呼びます。 現在でも、ライブラリとの連携などで頻繁に目にします。 Cスタイル文字列は、文字の並びの最後に「終端文字 `\0`(ヌル文字)」を置くことで終わりを表します。 diff --git a/public/docs/cpp/3-pointers/4-1-stack.md b/public/docs/cpp/3-pointers/4-1-stack.md index 5db20992..1fbe66e7 100644 --- a/public/docs/cpp/3-pointers/4-1-stack.md +++ b/public/docs/cpp/3-pointers/4-1-stack.md @@ -6,6 +6,8 @@ question: - スタックのサイズ制限とは、具体的にどのくらいのサイズを指すのか。 - 関数のスコープを抜けるとスタック上の変数が「自動的に消滅」するとは、メモリから完全に削除されるということか。 - 再帰呼び出しを多用するとスタックオーバーフローが起きると聞いたことがあるが、それはスタックの性質とどう関係があるのか。 +term: + - スタック --- ### スタック (Stack) diff --git a/public/docs/cpp/3-pointers/4-2-heap.md b/public/docs/cpp/3-pointers/4-2-heap.md index d8d1e71e..2810abc4 100644 --- a/public/docs/cpp/3-pointers/4-2-heap.md +++ b/public/docs/cpp/3-pointers/4-2-heap.md @@ -6,6 +6,10 @@ question: - '`new int(10);`と`new int;`の違いは何か。' - '`delete pInt;`と`delete[] pArray;`で`[]`がある場合とない場合の違いは何か。間違えて使ったらどうなるのか。' - メモリを解放した後にポインタを`nullptr`に設定する理由は何か。設定しないとどうなるのか。 +term: + - ヒープ + - new + - delete --- ### ヒープ (Heap) 領域と `new`, `delete` diff --git a/public/docs/cpp/3-pointers/4-4-memory-leak.md b/public/docs/cpp/3-pointers/4-4-memory-leak.md index 63f4bbb6..d7ea5361 100644 --- a/public/docs/cpp/3-pointers/4-4-memory-leak.md +++ b/public/docs/cpp/3-pointers/4-4-memory-leak.md @@ -7,18 +7,20 @@ question: - '`std::vector`や`std::string`が内部で`new`と`delete`を自動的に行ってくれるとは、具体的にどのような仕組みなのか。' - RAIIとは何か。なぜそれが生の`new/delete`よりも安全なのか。 - 生の`new/delete`を「最後の手段」とするのは、どのような状況を指すのか。 +term: + - メモリリーク --- ### 恐怖の「メモリリーク」 -もし `delete` を忘れるとどうなるでしょう? +もし [[`delete`]] を忘れるとどうなるでしょう? 確保されたメモリは、プログラムが終了するまで「使用中」のまま残ります。これを**メモリリーク**と呼びます。長時間動くサーバーなどでこれが起きると、メモリを食いつぶしてシステムがクラッシュします。 > [!TIP] > **[[./2]]の振り返り:** -> [[`std::vector`]] や [[`std::string`]] は、内部で `new` と `delete` を自動的に行ってくれています。 +> [[`std::vector`]] や [[`std::string`]] は、内部で [[`new`]] と [[`delete`]] を自動的に行ってくれています。 - * 作成時に `new` で確保。 - * スコープを抜けるときに自動で `delete`(デストラクタ)。 + * 作成時に [[`new`]] で確保。 + * スコープを抜けるときに自動で [[`delete`]](デストラクタ)。 これがC++のクラスの強力な機能(RAII)です。生の `new/delete` を直接使うことは、モダンC++では「最後の手段」あるいは「ライブラリを作る側の仕事」と考えられています。 diff --git a/public/docs/cpp/3-pointers/5-0-summary.md b/public/docs/cpp/3-pointers/5-0-summary.md index f7972e2a..1c949b84 100644 --- a/public/docs/cpp/3-pointers/5-0-summary.md +++ b/public/docs/cpp/3-pointers/5-0-summary.md @@ -7,9 +7,9 @@ question: [] ## この章のまとめ -1. **ポインタ**はメモリアドレスを保持する[[変数]]。`&`で取得、`*`でアクセス。 -2. ポインタの[[初期化]]には `nullptr` を使う。 +1. **[[ポインタ]]**はメモリアドレスを保持する[[変数]]。`&`で取得、`*`でアクセス。 +2. ポインタの[[初期化]]には [[`nullptr`]] を使う。 3. **配列名**は先頭要素へのポインタとして振る舞う(減衰)。 4. `ptr + i` は、`ptr` の指す型 `i` 個分先のアドレスを指す。 -5. **ヒープメモリ**は `new` で確保し、必ず `delete` で解放する。 -6. `delete` を忘れると**メモリリーク**になる。これを防ぐために `std::vector` などのコンテナクラスが存在する。 +5. **[[ヒープ]]メモリ**は [[`new`]] で確保し、必ず [[`delete`]] で解放する。 +6. `delete` を忘れると**[[メモリリーク]]**になる。これを防ぐために [[`std::vector`]] などのコンテナクラスが存在する。 diff --git a/public/docs/cpp/3-pointers/5-1-practice1.md b/public/docs/cpp/3-pointers/5-1-practice1.md index 594b5ed6..ea630c2d 100644 --- a/public/docs/cpp/3-pointers/5-1-practice1.md +++ b/public/docs/cpp/3-pointers/5-1-practice1.md @@ -9,7 +9,7 @@ question: ### 練習問題1: ポインタによる配列操作 -[[`int`]] 型のCスタイル配列 `arr` について、 `int*` 型のポインタを使って走査し、**すべての値を2倍に書き換えてください**(`[]` 演算子は使わず、ポインタ演算 `*` と `++` または `+` を使用すること)。 +[[`int`]] 型の[[Cスタイル配列]] `arr` について、 `int*` 型の[[ポインタ]]を使って走査し、**すべての値を2倍に書き換えてください**(`[]` 演算子は使わず、ポインタ演算 `*` と `++` または `+` を使用すること)。 ```cpp:practice4_1.cpp #include diff --git a/public/docs/cpp/3-pointers/5-2-practice2.md b/public/docs/cpp/3-pointers/5-2-practice2.md index 77db1520..fc79e11b 100644 --- a/public/docs/cpp/3-pointers/5-2-practice2.md +++ b/public/docs/cpp/3-pointers/5-2-practice2.md @@ -9,7 +9,7 @@ question: ### 問題2:手動メモリ管理の体験 -`n` 個の整数を格納できる配列を**ヒープ領域(`new`)**に確保してください。 +`n` 個の整数を格納できる配列を**[[ヒープ]]領域([[`new`]])**に確保してください。 その配列に 0 から `n-1` までの数値を代入し、合計値を計算して表示してください。 最後に、確保したメモリを適切に解放してください。 diff --git a/public/docs/cpp/4-functions/-intro.md b/public/docs/cpp/4-functions/-intro.md index a328d955..a1f36b51 100644 --- a/public/docs/cpp/4-functions/-intro.md +++ b/public/docs/cpp/4-functions/-intro.md @@ -1,3 +1,3 @@ -[[./3]]では、C++のメモリモデルの核心である「ポインタ」について学びました。ポインタは強力ですが、構文が複雑になりがちで、バグの温床にもなりえます。 +[[./3]]では、C++のメモリモデルの核心である「[[ポインタ]]」について学びました。ポインタは強力ですが、構文が複雑になりがちで、バグの温床にもなりえます。 C++では、C言語から受け継いだポインタに加え、より安全で直感的な**「参照(Reference)」**という概念が導入されています。本章では、関数の設計を通して、この「参照」がいかに強力な武器になるかを学びます。「データをどう渡すか」は、C++のパフォーマンスと設計の良し悪しを決める最も重要な要素の一つです。 diff --git a/public/docs/cpp/4-functions/2-2-arg-by-pointer.md b/public/docs/cpp/4-functions/2-2-arg-by-pointer.md index a0443684..88f30c12 100644 --- a/public/docs/cpp/4-functions/2-2-arg-by-pointer.md +++ b/public/docs/cpp/4-functions/2-2-arg-by-pointer.md @@ -10,10 +10,10 @@ question: ### 2\. ポインタ渡し (Pass by Pointer) -C言語からある手法です。[[./3]]で学んだポインタ(アドレス)を渡します。 +C言語からある手法です。[[./3]]で学んだ[[ポインタ]](アドレス)を渡します。 - * **メリット:** コピーが発生しない(アドレス値のコピーのみ)。呼び出し元のデータを変更できる。 - * **デメリット:** 呼び出す際に `&` を付ける必要がある。関数内で `*` や `->` を使う必要があり、構文が汚れる。`nullptr` チェックが必要になることがある。 + * **メリット:** コピーが発生しない([[アドレス]]値のコピーのみ)。呼び出し元のデータを変更できる。 + * **デメリット:** 呼び出す際に `&` を付ける必要がある。関数内で `*` や `->` を使う必要があり、構文が汚れる。[[`nullptr`]] チェックが必要になることがある。 diff --git a/public/docs/cpp/4-functions/2-3-arg-by-reference.md b/public/docs/cpp/4-functions/2-3-arg-by-reference.md index aab88051..50ea7928 100644 --- a/public/docs/cpp/4-functions/2-3-arg-by-reference.md +++ b/public/docs/cpp/4-functions/2-3-arg-by-reference.md @@ -12,7 +12,7 @@ question: C++の真骨頂です。**「参照(Reference)」**とは、既存の[[変数]]に別の名前(エイリアス)をつける機能です。引数の型に `&` を付けるだけで宣言できます。 - * **メリット:** コピーが発生しない。**構文は「値渡し」と同じように書ける**(`*`や`&`を呼び出し側で意識しなくていい)。`nullptr` になることがないため安全性が高い。 + * **メリット:** コピーが発生しない。**構文は「値渡し」と同じように書ける**(`*`や`&`を呼び出し側で意識しなくていい)。[[`nullptr`]] になることがないため安全性が高い。 * **デメリット:** 関数内で値を変更すると、呼び出し元も変わる(意図しない変更に注意)。 diff --git a/public/docs/cpp/4-functions/4-0-summary.md b/public/docs/cpp/4-functions/4-0-summary.md index 51a2943b..e63ed69d 100644 --- a/public/docs/cpp/4-functions/4-0-summary.md +++ b/public/docs/cpp/4-functions/4-0-summary.md @@ -9,7 +9,7 @@ question: [] * **プロトタイプ宣言**を使うことで、関数の定義順序に依存せずに記述できる。 * **値渡し**は安全だが、大きなオブジェクトではコピーコストがかかる。 - * **参照渡し (`&`)** は、ポインタのような効率性を持ちながら、[[変数]]のエイリアスとして直感的に扱える。 + * **参照渡し (`&`)** は、[[ポインタ]]のような効率性を持ちながら、[[変数]]のエイリアスとして直感的に扱える。 * **`const` 参照渡し (`const T&`)** は、大きなデータを「読み取り専用」で効率的に渡すC++の定石である。 * **オーバーロード**により、同じ名前で異なる引数を受け取る関数を作れる。 * **デフォルト引数**で、呼び出し時の記述を省略できる。 diff --git a/public/docs/cpp/4-functions/4-1-practice1.md b/public/docs/cpp/4-functions/4-1-practice1.md index d8d23146..058e9da7 100644 --- a/public/docs/cpp/4-functions/4-1-practice1.md +++ b/public/docs/cpp/4-functions/4-1-practice1.md @@ -10,7 +10,7 @@ question: ### 練習問題1: 値の入れ替え(Swap) 2つの `int` [[変数]]を受け取り、その値を入れ替える関数 `mySwap` を作成してください。 -ポインタではなく、**参照渡し**を使用してください。 +[[ポインタ]]ではなく、**参照渡し**を使用してください。 ```cpp:practice5_1.cpp #include diff --git a/public/docs/cpp/7-classes-advanced/1-0-copy.md b/public/docs/cpp/7-classes-advanced/1-0-copy.md index 9dd1c6fe..ffac8c97 100644 --- a/public/docs/cpp/7-classes-advanced/1-0-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-0-copy.md @@ -19,4 +19,4 @@ Vector2D v1(1.0, 2.0); Vector2D v2 = v1; // ここでコピーが発生! ``` -多くの場合、コンパイラが自動的に生成するコピー機能で十分です。しかし、クラスがポインタなどでリソース(メモリなど)を管理している場合、単純なコピーでは問題が発生します。 +多くの場合、コンパイラが自動的に生成するコピー機能で十分です。しかし、クラスが[[ポインタ]]などでリソース(メモリなど)を管理している場合、単純なコピーでは問題が発生します。 diff --git a/public/docs/cpp/7-classes-advanced/1-1-shallow-copy.md b/public/docs/cpp/7-classes-advanced/1-1-shallow-copy.md index 677937d0..4a2fa767 100644 --- a/public/docs/cpp/7-classes-advanced/1-1-shallow-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-1-shallow-copy.md @@ -18,7 +18,7 @@ question: まず、コピーの機能を自分で作らなかった場合に何が起きるか見てみましょう。 コンパイラは、メンバ変数を単純にコピーするだけの「浅いコピー」を行います。 -ここでは、`int`へのポインタを一つだけ持つ`ResourceHolder`(リソース保持者)というクラスを考えます。 +ここでは、`int`への[[ポインタ]]を一つだけ持つ`ResourceHolder`(リソース保持者)というクラスを考えます。 ```cpp:shallow_copy.cpp // 悪い例:浅いコピーの問題点 @@ -56,4 +56,4 @@ Resource 107521 destroyed. (at 0x1a4012b0) free(): double free detected in tcache 2 ``` -この例では、`r2`が作られるときに`r1`のポインタ`m_data`の値(メモリアドレス)だけがコピーされます。その結果、2つのオブジェクトが1つのメモリ領域を指してしまいます。プログラム終了時にそれぞれのデストラクタが呼ばれ、同じメモリを2回解放しようとしてエラーになります。 +この例では、`r2`が作られるときに`r1`の[[ポインタ]]`m_data`の値(メモリアドレス)だけがコピーされます。その結果、2つのオブジェクトが1つのメモリ領域を指してしまいます。プログラム終了時にそれぞれのデストラクタが呼ばれ、同じメモリを2回解放しようとしてエラーになります。 diff --git a/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md b/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md index 524e2507..2300d02b 100644 --- a/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md @@ -14,7 +14,7 @@ question: ### 解決策:コピー機能を自作する (深いコピー) -この問題を解決するために、**コピーコンストラクタ**と**コピー代入演算子**を自分で定義して、「深いコピー」を実装します。深いコピーとは、ポインタの指す先の実体(データそのもの)を新しく作ってコピーすることです。 +この問題を解決するために、**コピーコンストラクタ**と**コピー代入演算子**を自分で定義して、「深いコピー」を実装します。深いコピーとは、[[ポインタ]]の指す先の実体(データそのもの)を新しく作ってコピーすることです。 ```cpp:resource_holder.cpp #include @@ -122,11 +122,11 @@ Resource 10 destroyed. (at 0x139f065e0) *(メモリアドレスは実行するたびに変わります)* -実行結果を見ると、`rh1`, `rh2`, `rh3` はそれぞれ異なるメモリアドレス (`Address`) を持っていることがわかります。これにより、各オブジェクトは独立したリソースを管理でき、プログラム終了時にそれぞれのデストラクタが安全にメモリを解放できます。 +実行結果を見ると、`rh1`, `rh2`, `rh3` はそれぞれ異なるメモリ[[アドレス]] (`Address`) を持っていることがわかります。これにより、各オブジェクトは独立したリソースを管理でき、プログラム終了時にそれぞれのデストラクタが安全にメモリを解放できます。 | 機能 | いつ呼ばれるか | 何をするか | | :--- | :--- | :--- | | **コピーコンストラクタ** | オブジェクトが**作られる時**に、他のオブジェクトで[[初期化]]される場合
`ResourceHolder r2 = r1;` | 新しいリソースを確保し、元のオブジェクトの**値**をコピーする。 | | **コピー代入演算子** | **既にあるオブジェクト**に、他のオブジェクトを代入する場合
`r3 = r1;` | 1. 自分が持っている古いリソースを解放する。
2. 新しいリソースを確保し、元のオブジェクトの**値**をコピーする。 | -このように、ポインタでリソースを管理するクラスでは、安全なコピーを実現するためにこの2つの関数を自分で定義することが不可欠です。 +このように、[[ポインタ]]でリソースを管理するクラスでは、安全なコピーを実現するためにこの2つの関数を自分で定義することが不可欠です。 diff --git a/public/docs/cpp/7-classes-advanced/4-0-this.md b/public/docs/cpp/7-classes-advanced/4-0-this.md index fa707373..8cf0cd61 100644 --- a/public/docs/cpp/7-classes-advanced/4-0-this.md +++ b/public/docs/cpp/7-classes-advanced/4-0-this.md @@ -10,9 +10,9 @@ question: ## thisポインタ -非staticなメンバ関数が呼び出されるとき、その関数は「どのオブジェクトに対して呼び出されたか」を知る必要があります。コンパイラは、そのメンバ関数に対して、呼び出し元のオブジェクトのアドレスを暗黙的に渡します。このアドレスを保持するのが `this` ポインタです。 +非staticなメンバ関数が呼び出されるとき、その関数は「どのオブジェクトに対して呼び出されたか」を知る必要があります。コンパイラは、そのメンバ関数に対して、呼び出し元のオブジェクトの[[アドレス]]を暗黙的に渡します。このアドレスを保持するのが `this` ポインタです。 -`this` は、メンバ関数内で使用できるキーワードで、自分自身のオブジェクトを指すポインタです。 +`this` は、メンバ関数内で使用できるキーワードで、自分自身のオブジェクトを指す[[ポインタ]]です。 `this` ポインタが主に使われるのは、以下のような場面です。 @@ -25,7 +25,7 @@ question: } ``` -2. **自分自身の参照やポインタを返す場合** +2. **自分自身の参照や[[ポインタ]]を返す場合** コピー代入演算子で `return *this;` としたように、オブジェクト自身を返したい場合に使います。これにより、**メソッドチェーン**(`obj.setX(10).setY(20);` のような連続したメソッド呼び出し)が可能になります。 メソッドチェーンを実現する簡単な例を見てみましょう。 diff --git a/public/docs/cpp/7-classes-advanced/5-0-summary.md b/public/docs/cpp/7-classes-advanced/5-0-summary.md index 3b990f9a..4476a8dc 100644 --- a/public/docs/cpp/7-classes-advanced/5-0-summary.md +++ b/public/docs/cpp/7-classes-advanced/5-0-summary.md @@ -9,9 +9,9 @@ question: [] この章では、クラスをより効果的に利用するための応用的な機能を学びました。 - * **オブジェクトのコピー**: ポインタなどリソースを管理するクラスでは、**コピーコンストラクタ**と**コピー代入演算子**を定義し、**深いコピー**を実装することが重要です。これにより、リソースの二重解放などの問題を未然に防ぎます。 + * **オブジェクトのコピー**: [[ポインタ]]などリソースを管理するクラスでは、**コピーコンストラクタ**と**コピー代入演算子**を定義し、**深いコピー**を実装することが重要です。これにより、リソースの二重解放などの問題を未然に防ぎます。 * **演算子のオーバーロード**: `+` や `==` などの演算子を自作クラスに対して定義することで、コードの可読性を高め、直感的な操作を可能にします。 * **staticメンバ**: `static`メンバ変数やメンバ関数は、クラスの全オブジェクトで共有されるデータや機能を提供します。オブジェクトを生成しなくてもアクセスできるのが特徴です。 - * **thisポインタ**: 非staticメンバ関数内で、呼び出し元のオブジェクト自身を指すポインタです。メンバ変数と引数の区別や、メソッドチェーンの実装に役立ちます。 + * **thisポインタ**: 非staticメンバ関数内で、呼び出し元のオブジェクト自身を指す[[ポインタ]]です。メンバ変数と引数の区別や、メソッドチェーンの実装に役立ちます。 これらの機能を組み合わせることで、C++のクラスは単なるデータの入れ物から、振る舞いを伴った洗練された部品へと進化します。 diff --git a/public/docs/cpp/7-classes-advanced/5-2-practice2.md b/public/docs/cpp/7-classes-advanced/5-2-practice2.md index 0b30919f..76ce389e 100644 --- a/public/docs/cpp/7-classes-advanced/5-2-practice2.md +++ b/public/docs/cpp/7-classes-advanced/5-2-practice2.md @@ -10,7 +10,7 @@ question: ### 練習問題2: 動的配列クラスのコピー制御 -整数 (`int`) の動的配列を管理するクラス `IntArray` を作成してください。このクラスは、コンストラクタで指定されたサイズの配列を `new` で確保し、デストラクタで `delete[]` を使って解放します。 +整数 (`int`) の動的配列を管理するクラス `IntArray` を作成してください。このクラスは、コンストラクタで指定されたサイズの配列を [[`new`]] で確保し、デストラクタで `delete[]` を使って解放します。 この `IntArray` クラスに対して、**深いコピー**を正しく行うための**コピーコンストラクタ**と**コピー代入演算子**を実装してください。 diff --git a/public/docs/cpp/8-inheritance/2-0-polymorphism.md b/public/docs/cpp/8-inheritance/2-0-polymorphism.md index 852bda06..9290b4a8 100644 --- a/public/docs/cpp/8-inheritance/2-0-polymorphism.md +++ b/public/docs/cpp/8-inheritance/2-0-polymorphism.md @@ -15,7 +15,7 @@ question: これを実現するのが **仮想関数 (virtual function)** です。親クラスの関数宣言の前に `virtual` キーワードを付けると、その関数は仮想関数になります。 -親クラスのポインタや参照は、子クラスのオブジェクトを指すことができます。このとき、呼び出された仮想関数は、ポインタが指している**オブジェクトの実際の型**に基づいて決定されます。 +親クラスの[[ポインタ]]や参照は、子クラスのオブジェクトを指すことができます。このとき、呼び出された仮想関数は、[[ポインタ]]が指している**オブジェクトの実際の型**に基づいて決定されます。 言葉だけでは難しいので、コードで見てみましょう。 @@ -73,4 +73,4 @@ Woof! Meow! ``` -`make_animal_speak` 関数は `Animal*` 型の引数を取りますが、`Dog`オブジェクトや`Cat`オブジェクトのアドレスを渡すことができています。そして、`animal->speak()` を呼び出すと、`animal` ポインタが実際に指しているオブジェクトの `speak()` が実行されます。これがポリモーフィズムです。もし `Animal`クラスの `speak()` に `virtual` が付いていなければ、どのオブジェクトを渡しても `Animal` の `speak()` が呼ばれてしまいます。 +`make_animal_speak` 関数は `Animal*` 型の引数を取りますが、`Dog`オブジェクトや`Cat`オブジェクトの[[アドレス]]を渡すことができています。そして、`animal->speak()` を呼び出すと、`animal` ポインタが実際に指しているオブジェクトの `speak()` が実行されます。これがポリモーフィズムです。もし `Animal`クラスの `speak()` に `virtual` が付いていなければ、どのオブジェクトを渡しても `Animal` の `speak()` が呼ばれてしまいます。 diff --git a/public/docs/cpp/8-inheritance/5-0-summary.md b/public/docs/cpp/8-inheritance/5-0-summary.md index 32a747f1..bf66a941 100644 --- a/public/docs/cpp/8-inheritance/5-0-summary.md +++ b/public/docs/cpp/8-inheritance/5-0-summary.md @@ -9,6 +9,6 @@ question: [] * **継承**: 既存のクラスの機能を引き継ぎ、コードの再利用性を高める仕組みです。`(子クラス) : public (親クラス)` のように書きます。 * **ポリモーフィズム**: 「同じ指示でも、オブジェクトの種類によって異なる振る舞いをさせる」性質です。 - * **仮想関数 (`virtual`)**: ポリモーフィズムを実現するための鍵です。親クラスの関数に `virtual` を付けると、ポインタや参照経由で呼び出した際に、オブジェクトの実際の型に応じた関数が実行されます。 + * **仮想関数 (`virtual`)**: ポリモーフィズムを実現するための鍵です。親クラスの関数に `virtual` を付けると、[[ポインタ]]や参照経由で呼び出した際に、オブジェクトの実際の型に応じた関数が実行されます。 * **オーバーライド (`override`)**: 子クラスで親クラスの仮想関数を上書きする意図を明示します。コンパイラがチェックしてくれるため、安全性が向上します。 * **抽象クラス**: 1つ以上の**純粋仮想関数 (`virtual ... = 0;`)** を持つクラスです。インスタンス化できず、継承されるための設計図として機能します。 diff --git a/public/docs/cpp/8-inheritance/5-1-practice1.md b/public/docs/cpp/8-inheritance/5-1-practice1.md index 682c08bc..4459a4d2 100644 --- a/public/docs/cpp/8-inheritance/5-1-practice1.md +++ b/public/docs/cpp/8-inheritance/5-1-practice1.md @@ -11,7 +11,7 @@ question: `Vehicle` という親クラスを作成し、`move()` というメンバ関数を持たせましょう。次に、`Vehicle` を継承して `Car` クラスと `Motorcycle` クラスを作成し、それぞれが独自の `move()` の振る舞いをするようにオーバーライドしてください。 -[[`main` 関数]]では、`Vehicle` のポインタの配列を作成し、`Car` と `Motorcycle` のオブジェクトを格納して、ループでそれぞれの `move()` を呼び出してください。 +[[`main` 関数]]では、`Vehicle` の[[ポインタ]]の配列を作成し、`Car` と `Motorcycle` のオブジェクトを格納して、ループでそれぞれの `move()` を呼び出してください。 ```cpp:practice9_1.cpp #include From ef88fbc63ba8b3d3cc94c976a1adcaeeadb47b7d Mon Sep 17 00:00:00 2001 From: na-trium-144 <100704180+na-trium-144@users.noreply.github.com> Date: Sun, 9 Aug 2026 15:27:19 +0900 Subject: [PATCH 5/9] c++ 4 --- public/docs/cpp/11-stl-algorithms/3-0-lambda.md | 6 +++--- .../cpp/4-functions/1-1-prototype-declaration.md | 2 ++ public/docs/cpp/4-functions/1-2-void.md | 2 ++ public/docs/cpp/4-functions/2-1-arg-by-value.md | 5 +++++ public/docs/cpp/4-functions/2-2-arg-by-pointer.md | 2 ++ public/docs/cpp/4-functions/2-3-arg-by-reference.md | 7 ++++++- .../cpp/4-functions/2-4-arg-by-const-reference.md | 11 +++++------ public/docs/cpp/4-functions/3-1-overload.md | 2 ++ public/docs/cpp/4-functions/3-2-default-arg.md | 4 +++- public/docs/cpp/4-functions/4-0-summary.md | 12 ++++++------ public/docs/cpp/4-functions/4-1-practice1.md | 2 +- public/docs/cpp/4-functions/4-2-practice2.md | 2 +- .../cpp/5-project-build/1-0-header-and-source.md | 2 +- public/docs/cpp/6-classes-basics/4-1-constructor.md | 4 ++-- public/docs/cpp/7-classes-advanced/1-0-copy.md | 2 +- .../cpp/7-classes-advanced/2-0-operator-overload.md | 2 +- 16 files changed, 43 insertions(+), 24 deletions(-) diff --git a/public/docs/cpp/11-stl-algorithms/3-0-lambda.md b/public/docs/cpp/11-stl-algorithms/3-0-lambda.md index f5e1f049..e57f1b38 100644 --- a/public/docs/cpp/11-stl-algorithms/3-0-lambda.md +++ b/public/docs/cpp/11-stl-algorithms/3-0-lambda.md @@ -23,9 +23,9 @@ question: * `[]` **キャプチャ句**: ラムダ式の外にある[[変数]]を取り込んで、式の中で使えるようにします。 * `[]`: 何もキャプチャしない。 - * `[=]`: 外の変数を全て値渡し(コピー)でキャプチャする。 - * `[&]`: 外の変数を全て参照渡しでキャプチャする。 - * `[x, &y]`: 変数 `x` は値渡し、変数 `y` は参照渡しでキャプチャする。 + * `[=]`: 外の変数を全て[[値渡し]](コピー)でキャプチャする。 + * `[&]`: 外の変数を全て[[参照渡し]]でキャプチャする。 + * `[x, &y]`: 変数 `x` は[[値渡し]]、変数 `y` は[[参照渡し]]でキャプチャする。 * `()` **引数リスト**:通常の関数と同じ引数を取ることができます。 * `-> 戻り値の型`: 戻り値の型を指定します。多くの場合、コンパイラが推論できるため省略可能です。 * `{}` **処理本体**: 関数の処理内容を記述します。 diff --git a/public/docs/cpp/4-functions/1-1-prototype-declaration.md b/public/docs/cpp/4-functions/1-1-prototype-declaration.md index 9e74c2e8..45284352 100644 --- a/public/docs/cpp/4-functions/1-1-prototype-declaration.md +++ b/public/docs/cpp/4-functions/1-1-prototype-declaration.md @@ -7,6 +7,8 @@ question: - 関数をmain関数の後に定義するメリットは何ですか? - プロトタイプ宣言では引数名を省略しても良いのですか? - プロトタイプ宣言の最後にセミコロンが必要な理由は何ですか? +term: + - プロトタイプ宣言 --- ### プロトタイプ宣言 diff --git a/public/docs/cpp/4-functions/1-2-void.md b/public/docs/cpp/4-functions/1-2-void.md index af100af6..1874815e 100644 --- a/public/docs/cpp/4-functions/1-2-void.md +++ b/public/docs/cpp/4-functions/1-2-void.md @@ -6,6 +6,8 @@ question: - void型は「型がない」とのことですが、具体的にどのような場面で使われることが多いですか? - void型の変数を定義できないのはなぜですか? - 戻り値がない関数の中で、`return;` とだけ書くことはできますか? +term: + - void --- ### 戻り値がない場合: `void`型 diff --git a/public/docs/cpp/4-functions/2-1-arg-by-value.md b/public/docs/cpp/4-functions/2-1-arg-by-value.md index f645251b..76274aa7 100644 --- a/public/docs/cpp/4-functions/2-1-arg-by-value.md +++ b/public/docs/cpp/4-functions/2-1-arg-by-value.md @@ -6,6 +6,8 @@ question: - 値渡しで変数の「コピーが作成される」とは、メモリ上で具体的に何が起きるのですか? - 巨大な配列やオブジェクトを渡す際、「コストが高い」とはどのくらいのサイズからを指しますか? - 関数内で引数の値を変更しても呼び出し元に影響しないのは、どのような場合にメリットになりますか? +term: + - 値渡し --- ### 1\. 値渡し (Pass by Value) @@ -15,6 +17,9 @@ question: * **メリット:** 安全。関数内で値を変更しても、呼び出し元の[[変数]]には影響しない。 * **デメリット:** コストが高い。巨大な配列やオブジェクトを渡す際、丸ごとコピーするためメモリと時間を浪費する。 +> [!TIP] +> `int` や `double` などの[[基本型]] → **値渡し** でOK。 + ```cpp:pass_by_value.cpp diff --git a/public/docs/cpp/4-functions/2-2-arg-by-pointer.md b/public/docs/cpp/4-functions/2-2-arg-by-pointer.md index 88f30c12..55eade7c 100644 --- a/public/docs/cpp/4-functions/2-2-arg-by-pointer.md +++ b/public/docs/cpp/4-functions/2-2-arg-by-pointer.md @@ -6,6 +6,8 @@ question: - ポインタ渡しで「構文が汚れる」とは具体的にどのようなことですか? - ポインタ渡しで`nullptr`チェックが必要な理由は何ですか? - '`nullptr`を渡してしまった場合、どのような問題が起こりえますか?' +term: + - ポインタ渡し --- ### 2\. ポインタ渡し (Pass by Pointer) diff --git a/public/docs/cpp/4-functions/2-3-arg-by-reference.md b/public/docs/cpp/4-functions/2-3-arg-by-reference.md index 50ea7928..b1808b09 100644 --- a/public/docs/cpp/4-functions/2-3-arg-by-reference.md +++ b/public/docs/cpp/4-functions/2-3-arg-by-reference.md @@ -6,15 +6,20 @@ question: - 「参照(Reference)」が既存の変数に別の名前をつける機能とは、具体的にどのようなイメージですか? - 参照渡しは`nullptr`にならないとのことですが、なぜですか? - 参照渡しで「意図しない変更に注意」とありますが、どのような場合に問題になりますか? +term: + - 参照渡し --- ### 3\. 参照渡し (Pass by Reference) C++の真骨頂です。**「参照(Reference)」**とは、既存の[[変数]]に別の名前(エイリアス)をつける機能です。引数の型に `&` を付けるだけで宣言できます。 - * **メリット:** コピーが発生しない。**構文は「値渡し」と同じように書ける**(`*`や`&`を呼び出し側で意識しなくていい)。[[`nullptr`]] になることがないため安全性が高い。 + * **メリット:** コピーが発生しない。**構文は「[[値渡し]]」と同じように書ける**(`*`や`&`を呼び出し側で意識しなくていい)。[[`nullptr`]] になることがないため安全性が高い。 * **デメリット:** 関数内で値を変更すると、呼び出し元も変わる(意図しない変更に注意)。 +> [!TIP] +> 変更させたいデータ → **参照渡し** (`T&`)。 + ```cpp:pass_by_ref.cpp diff --git a/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md b/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md index eb867b3e..1276748d 100644 --- a/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md +++ b/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md @@ -6,6 +6,8 @@ question: - '`const`参照渡しがC++で最も頻繁に使われるパターンとされるのはなぜですか?' - '`const`参照渡しで関数内で値を変更しようとするとコンパイルエラーになるのは、具体的にどのような仕組みですか?' - '`int`や`double`のような基本型では値渡しで良いとのことですが、なぜ`const`参照渡しを使う必要がないのですか?' +term: + - const 参照渡し --- ### 4\. const 参照渡し (Pass by const Reference) @@ -17,6 +19,9 @@ question: +> [!TIP] +> 変更しないがサイズが大きいデータ([[`std::string`]], [[`std::vector`]]など) → **const参照渡し** (`const T&`)。 + ```cpp:const_ref.cpp #include #include @@ -42,9 +47,3 @@ int main() { ```cpp-exec:const_ref.cpp Message: This is a potentially very large string... ``` - -> **ガイドライン:** -> -> * `int` や `double` などの[[基本型]] → **値渡し** でOK。 -> * 変更させたいデータ → **参照渡し** (`T&`)。 -> * 変更しないがサイズが大きいデータ([[`std::string`]], [[`std::vector`]]など) → **const参照渡し** (`const T&`)。 diff --git a/public/docs/cpp/4-functions/3-1-overload.md b/public/docs/cpp/4-functions/3-1-overload.md index e2dcf0a9..26a6c748 100644 --- a/public/docs/cpp/4-functions/3-1-overload.md +++ b/public/docs/cpp/4-functions/3-1-overload.md @@ -6,6 +6,8 @@ question: - C言語では関数名がユニークである必要があったのに、C++でオーバーロードが可能になったのはなぜですか? - 戻り値の型だけが異なる関数を同じ名前で定義することはできますか? - オーバーロードされた関数を呼び出す際に、意図しない関数が呼び出されるようなことはありませんか? +term: + - オーバーロード --- ### オーバーロード (Function Overloading) diff --git a/public/docs/cpp/4-functions/3-2-default-arg.md b/public/docs/cpp/4-functions/3-2-default-arg.md index 5ddee356..afef412a 100644 --- a/public/docs/cpp/4-functions/3-2-default-arg.md +++ b/public/docs/cpp/4-functions/3-2-default-arg.md @@ -6,11 +6,13 @@ question: - デフォルト引数を「後ろの引数から順に」設定する必要があるのはなぜですか? - デフォルト引数を設定した場合でも、すべての引数を明示的に指定して関数を呼び出すことはできますか? - デフォルト引数はプロトタイプ宣言と定義の両方に記述するべきですか? +term: + - デフォルト引数 --- ### デフォルト引数 -引数が省略された場合に使われるデフォルト値を設定できます。これはプロトタイプ宣言(または最初にコンパイラが見る定義)に記述します。 +引数が省略された場合に使われるデフォルト値を設定できます。これは[[プロトタイプ宣言]](または最初にコンパイラが見る定義)に記述します。 ※デフォルト引数は**後ろの引数から順に**設定する必要があります。 ```cpp:default_args.cpp diff --git a/public/docs/cpp/4-functions/4-0-summary.md b/public/docs/cpp/4-functions/4-0-summary.md index e63ed69d..b053f1a6 100644 --- a/public/docs/cpp/4-functions/4-0-summary.md +++ b/public/docs/cpp/4-functions/4-0-summary.md @@ -7,9 +7,9 @@ question: [] ## この章のまとめ - * **プロトタイプ宣言**を使うことで、関数の定義順序に依存せずに記述できる。 - * **値渡し**は安全だが、大きなオブジェクトではコピーコストがかかる。 - * **参照渡し (`&`)** は、[[ポインタ]]のような効率性を持ちながら、[[変数]]のエイリアスとして直感的に扱える。 - * **`const` 参照渡し (`const T&`)** は、大きなデータを「読み取り専用」で効率的に渡すC++の定石である。 - * **オーバーロード**により、同じ名前で異なる引数を受け取る関数を作れる。 - * **デフォルト引数**で、呼び出し時の記述を省略できる。 + * **[[プロトタイプ宣言]]**を使うことで、関数の定義順序に依存せずに記述できる。 + * **[[値渡し]]**は安全だが、大きなオブジェクトではコピーコストがかかる。 + * **[[参照渡し]] (`&`)** は、[[ポインタ]]のような効率性を持ちながら、[[変数]]のエイリアスとして直感的に扱える。 + * **[[`const` 参照渡し]] (`const T&`)** は、大きなデータを「読み取り専用」で効率的に渡すC++の定石である。 + * **[[オーバーロード]]**により、同じ名前で異なる引数を受け取る関数を作れる。 + * **[[デフォルト引数]]**で、呼び出し時の記述を省略できる。 diff --git a/public/docs/cpp/4-functions/4-1-practice1.md b/public/docs/cpp/4-functions/4-1-practice1.md index 058e9da7..0d6fe376 100644 --- a/public/docs/cpp/4-functions/4-1-practice1.md +++ b/public/docs/cpp/4-functions/4-1-practice1.md @@ -10,7 +10,7 @@ question: ### 練習問題1: 値の入れ替え(Swap) 2つの `int` [[変数]]を受け取り、その値を入れ替える関数 `mySwap` を作成してください。 -[[ポインタ]]ではなく、**参照渡し**を使用してください。 +[[ポインタ]]ではなく、**[[参照渡し]]**を使用してください。 ```cpp:practice5_1.cpp #include diff --git a/public/docs/cpp/4-functions/4-2-practice2.md b/public/docs/cpp/4-functions/4-2-practice2.md index c32114bd..f5251ce8 100644 --- a/public/docs/cpp/4-functions/4-2-practice2.md +++ b/public/docs/cpp/4-functions/4-2-practice2.md @@ -13,7 +13,7 @@ question: `std::vector` を受け取り、その中の「最大値」を見つけて返す関数 `findMax` を作成してください。 ただし、以下の条件を守ってください。 -1. ベクターはコピーされないようにしてください(**参照渡し**)。 +1. ベクターはコピーされないようにしてください(**[[参照渡し]]**)。 2. 関数内でベクターの内容が変更されないことを保証してください(**const**)。 3. ベクターが空の場合は `0` を返すなどの処理を入れてください。 diff --git a/public/docs/cpp/5-project-build/1-0-header-and-source.md b/public/docs/cpp/5-project-build/1-0-header-and-source.md index 2273e003..519d2af2 100644 --- a/public/docs/cpp/5-project-build/1-0-header-and-source.md +++ b/public/docs/cpp/5-project-build/1-0-header-and-source.md @@ -13,7 +13,7 @@ question: C++では、プログラムを**ヘッダファイル**と**ソースファイル**という2種類のファイルに分割するのが一般的です。 - * **ヘッダファイル (`.h` または `.hpp`)**: 「宣言」を置く場所です。クラスの定義、関数のプロトタイプ宣言、定数、テンプレートなどを記述します。他のファイルに対して「何ができるか(インターフェース)」を公開する役割を持ちます。 + * **ヘッダファイル (`.h` または `.hpp`)**: 「宣言」を置く場所です。クラスの定義、関数の[[プロトタイプ宣言]]、定数、テンプレートなどを記述します。他のファイルに対して「何ができるか(インターフェース)」を公開する役割を持ちます。 * **ソースファイル (`.cpp`)**: 「実装」を置く場所です。ヘッダファイルで宣言された関数の具体的な処理内容などを記述します。ヘッダファイルが公開したインターフェースを「どのように実現するか」を記述する役割を持ちます。 **なぜ分割するのか? 🤔** diff --git a/public/docs/cpp/6-classes-basics/4-1-constructor.md b/public/docs/cpp/6-classes-basics/4-1-constructor.md index 9c5b9eaa..7abefc38 100644 --- a/public/docs/cpp/6-classes-basics/4-1-constructor.md +++ b/public/docs/cpp/6-classes-basics/4-1-constructor.md @@ -16,8 +16,8 @@ question: コンストラクタには以下の特徴があります。 - 関数名がクラス名と全く同じ。 - - 戻り値の型を指定しない(`void`も付けない)。 - - 引数を取ることができ、複数定義できる(オーバーロード)。 + - 戻り値の型を指定しない([[`void`]]も付けない)。 + - 引数を取ることができ、複数定義できる([[オーバーロード]])。 ```cpp:constructor.cpp class Person { diff --git a/public/docs/cpp/7-classes-advanced/1-0-copy.md b/public/docs/cpp/7-classes-advanced/1-0-copy.md index ffac8c97..6a22e67f 100644 --- a/public/docs/cpp/7-classes-advanced/1-0-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-0-copy.md @@ -12,7 +12,7 @@ question: ## オブジェクトのコピー: コピーコンストラクタと代入演算子 -オブジェクトをコピーしたい場面は頻繁にあります。例えば、関数の引数にオブジェクトを渡すとき(値渡し)や、既存のオブジェクトで新しいオブジェクトを[[初期化]]するときなどです。 +オブジェクトをコピーしたい場面は頻繁にあります。例えば、関数の引数にオブジェクトを渡すとき([[値渡し]])や、既存のオブジェクトで新しいオブジェクトを[[初期化]]するときなどです。 ```cpp Vector2D v1(1.0, 2.0); diff --git a/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md b/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md index 4e34be9d..8541c3ae 100644 --- a/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md +++ b/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md @@ -13,7 +13,7 @@ question: ## 演算子のオーバーロード -C++では、`+`, `-`, `==`, `<<` などの組み込み演算子を、自作のクラスで使えるように**再定義(オーバーロード)**できます。これにより、クラスのインスタンスをあたかも組み込み型(`int`や`double`など)のように直感的に扱えるようになります。 +C++では、`+`, `-`, `==`, `<<` などの組み込み演算子を、自作のクラスで使えるように**再定義([[オーバーロード]])**できます。これにより、クラスのインスタンスをあたかも組み込み型(`int`や`double`など)のように直感的に扱えるようになります。 例えば、2次元ベクトルを表す `Vector2D` クラスがあるとします。`v3 = v1 + v2;` のように、ベクトル同士の足し算を自然に記述できると便利ですよね。 From 80cfb5e50930e981dab953a51b3216af63e79156 Mon Sep 17 00:00:00 2001 From: na-trium-144 <100704180+na-trium-144@users.noreply.github.com> Date: Sun, 9 Aug 2026 20:19:24 +0900 Subject: [PATCH 6/9] c++ 5 --- public/docs/cpp/0-intro/4-1-include.md | 2 +- public/docs/cpp/4-functions/1-1-prototype-declaration.md | 2 +- public/docs/cpp/5-project-build/1-0-header-and-source.md | 4 ++++ public/docs/cpp/5-project-build/1-2-split-example.md | 6 +++--- public/docs/cpp/5-project-build/2-0-include-guard.md | 8 +++++--- public/docs/cpp/5-project-build/2-2-pragma-once.md | 2 +- public/docs/cpp/5-project-build/3-0-build.md | 2 +- public/docs/cpp/5-project-build/3-1-gcc-manual.md | 2 +- public/docs/cpp/5-project-build/4-0-summary.md | 4 ++-- public/docs/cpp/7-classes-advanced/3-0-static-member.md | 2 +- 10 files changed, 20 insertions(+), 14 deletions(-) diff --git a/public/docs/cpp/0-intro/4-1-include.md b/public/docs/cpp/0-intro/4-1-include.md index f780c7a3..a5bac600 100644 --- a/public/docs/cpp/0-intro/4-1-include.md +++ b/public/docs/cpp/0-intro/4-1-include.md @@ -16,4 +16,4 @@ term: `#include` は、他のファイルに書かれた機能を利用するための**プリプロセッサ命令**です。ここでは、コンソールへの入出力機能を提供する `iostream` という標準ライブラリのヘッダファイルを読み込んでいます。これにより、`std::cout` などが使えるようになります。 * `< >` で囲む: 標準ライブラリのヘッダファイルをインクルードする場合 - * `" "` で囲む: 自分で作成したヘッダファイルをインクルードする場合 ([[./5]]で学びます) + * `" "` で囲む: 自分で作成した[[ヘッダファイル]]をインクルードする場合 ([[./5]]で学びます) diff --git a/public/docs/cpp/4-functions/1-1-prototype-declaration.md b/public/docs/cpp/4-functions/1-1-prototype-declaration.md index 45284352..c8d33759 100644 --- a/public/docs/cpp/4-functions/1-1-prototype-declaration.md +++ b/public/docs/cpp/4-functions/1-1-prototype-declaration.md @@ -47,4 +47,4 @@ Hello C++! Hello C++! ``` -実際の開発では、プロトタイプ宣言をヘッダーファイル(`.h`)に書き、定義をソースファイル(`.cpp`)に書くことで、大規模なプログラムを管理します(これについては[[./5]]で詳しく解説します)。 +実際の開発では、プロトタイプ宣言を[[ヘッダーファイル]](`.h`)に書き、定義を[[ソースファイル]](`.cpp`)に書くことで、大規模なプログラムを管理します(これについては[[./5]]で詳しく解説します)。 diff --git a/public/docs/cpp/5-project-build/1-0-header-and-source.md b/public/docs/cpp/5-project-build/1-0-header-and-source.md index 519d2af2..bb98798e 100644 --- a/public/docs/cpp/5-project-build/1-0-header-and-source.md +++ b/public/docs/cpp/5-project-build/1-0-header-and-source.md @@ -7,6 +7,10 @@ question: - ヘッダファイルの拡張子には.hと.hppのどちらを使うべきですか? - コンパイル時間の短縮とは、具体的にどのようなメリットがあるのですか? - 「関心の分離」によって、具体的にどんなコードの見通しが良くなるのでしょうか? +term: + - ヘッダファイル + - ヘッダーファイル + - ソースファイル --- ## ヘッダファイルとソースファイル diff --git a/public/docs/cpp/5-project-build/1-2-split-example.md b/public/docs/cpp/5-project-build/1-2-split-example.md index d3f501ab..6cea2553 100644 --- a/public/docs/cpp/5-project-build/1-2-split-example.md +++ b/public/docs/cpp/5-project-build/1-2-split-example.md @@ -11,7 +11,7 @@ question: 簡単な足し算を行う関数を別のファイルに分割してみましょう。 -まず、関数の「宣言」をヘッダファイルに記述します。 +まず、関数の「宣言」を[[ヘッダファイル]]に記述します。 ```cpp:math_utils.h // 関数の宣言を記述するヘッダファイル @@ -20,7 +20,7 @@ question: int add(int a, int b); ``` -次に、この関数の「実装」をソースファイルに記述します。 +次に、この関数の「実装」を[[ソースファイル]]に記述します。 ```cpp:math_utils.cpp // 関数の実装を記述するソースファイル @@ -32,7 +32,7 @@ int add(int a, int b) { } ``` -最後に、[[`main`関数]]を含むメインのソースファイルから、この`add`関数を呼び出します。 +最後に、[[`main`関数]]を含むメインの[[ソースファイル]]から、この`add`関数を呼び出します。 ```cpp:math_app.cpp #include diff --git a/public/docs/cpp/5-project-build/2-0-include-guard.md b/public/docs/cpp/5-project-build/2-0-include-guard.md index 98e55531..ebad9e70 100644 --- a/public/docs/cpp/5-project-build/2-0-include-guard.md +++ b/public/docs/cpp/5-project-build/2-0-include-guard.md @@ -6,13 +6,15 @@ question: - 「翻訳単位」とは何ですか? - 複数のファイルで同じヘッダがインクルードされたとき、どのようなエラーメッセージが出ますか? - インクルードガードがないと、必ずコンパイルエラーになりますか? +term: + - インクルードガード --- ## インクルードガード -複数のファイルから同じヘッダファイルが[[インクルード]]される状況はよくあります。例えば、`A.h`が`B.h`を[[インクルード]]し、ソースファイルが`A.h`と`B.h`の両方をインクルードするような場合です。 +複数のファイルから同じ[[ヘッダファイル]]が[[インクルード]]される状況はよくあります。例えば、`A.h`が`B.h`を[[インクルード]]し、[[ソースファイル]]が`A.h`と`B.h`の両方をインクルードするような場合です。 -もしヘッダファイルに何の対策もしていないと、同じ内容(クラス定義や関数宣言)が複数回読み込まれ、「再定義」としてコンパイルエラーが発生してしまいます。 +もし[[ヘッダファイル]]に何の対策もしていないと、同じ内容(クラス定義や関数宣言)が複数回読み込まれ、「再定義」としてコンパイルエラーが発生してしまいます。 ```cpp:A.h #include "B.h" // B.hをインクルード @@ -49,4 +51,4 @@ B.h:1:7: note: previous definition of 'class B' | ^ ``` -この問題を解決するのが**インクルードガード**です。インクルードガードは、ヘッダファイルの内容が1つの翻訳単位(ソースファイル)内で一度しか読み込まれないようにするための仕組みです。 +この問題を解決するのが**インクルードガード**です。インクルードガードは、[[ヘッダファイル]]の内容が1つの翻訳単位([[ソースファイル]])内で一度しか読み込まれないようにするための仕組みです。 diff --git a/public/docs/cpp/5-project-build/2-2-pragma-once.md b/public/docs/cpp/5-project-build/2-2-pragma-once.md index 3b9f6bab..d8c9fb9a 100644 --- a/public/docs/cpp/5-project-build/2-2-pragma-once.md +++ b/public/docs/cpp/5-project-build/2-2-pragma-once.md @@ -20,4 +20,4 @@ question: std::string to_upper(const std::string& str); ``` -この一行をヘッダファイルの先頭に書くだけで、コンパイラがそのファイルが一度しか[[インクルード]]されないように処理してくれます。特別な理由がない限り、現在では `#pragma once` を使うのが主流です。 +この一行を[[ヘッダファイル]]の先頭に書くだけで、コンパイラがそのファイルが一度しか[[インクルード]]されないように処理してくれます。特別な理由がない限り、現在では `#pragma once` を使うのが主流です。 diff --git a/public/docs/cpp/5-project-build/3-0-build.md b/public/docs/cpp/5-project-build/3-0-build.md index 85c68744..93aa8d6c 100644 --- a/public/docs/cpp/5-project-build/3-0-build.md +++ b/public/docs/cpp/5-project-build/3-0-build.md @@ -10,6 +10,6 @@ question: ## プロジェクトのビルド -複数のソースファイル(`.cpp`)は、それぞれが[[コンパイル]]されて**オブジェクトファイル**(`.o` や `.obj`)になります。その後、**リンカ**がこれらのオブジェクトファイルと必要なライブラリを結合して、最終的な実行可能ファイルを生成します。 +複数の[[ソースファイル]](`.cpp`)は、それぞれが[[コンパイル]]されて**オブジェクトファイル**(`.o` や `.obj`)になります。その後、**リンカ**がこれらのオブジェクトファイルと必要なライブラリを結合して、最終的な実行可能ファイルを生成します。 この一連の作業を**ビルド**と呼びます。ファイルが増えてくると、これを手動で行うのは非常に面倒です。そこで、ビルド作業を自動化する**ビルドシステム**が使われます。 diff --git a/public/docs/cpp/5-project-build/3-1-gcc-manual.md b/public/docs/cpp/5-project-build/3-1-gcc-manual.md index a9685d41..c567b789 100644 --- a/public/docs/cpp/5-project-build/3-1-gcc-manual.md +++ b/public/docs/cpp/5-project-build/3-1-gcc-manual.md @@ -24,7 +24,7 @@ g++ main.o math_utils.o -o my_app ./my_app ``` -または、以下のように1回のg++コマンドで複数ソースファイルのコンパイルとリンクを同時に行うこともできます。 +または、以下のように1回のg++コマンドで複数[[ソースファイル]]のコンパイルとリンクを同時に行うこともできます。 ```bash g++ math_app.cpp math_utils.cpp -o my_app diff --git a/public/docs/cpp/5-project-build/4-0-summary.md b/public/docs/cpp/5-project-build/4-0-summary.md index c2abe20b..b27ecd64 100644 --- a/public/docs/cpp/5-project-build/4-0-summary.md +++ b/public/docs/cpp/5-project-build/4-0-summary.md @@ -7,6 +7,6 @@ question: [] ## この章のまとめ - * **プロジェクトの分割**: プログラムは「宣言」を記述する**ヘッダファイル** (`.h`) と、「実装」を記述する**ソースファイル** (`.cpp`) に分割することで、保守性や再利用性が向上します。 - * **インクルードガード**: ヘッダファイルの多重インクルードによる再定義エラーを防ぐために、`#pragma once` や `#ifndef`/`#define`/`#endif` を使用します。 + * **プロジェクトの分割**: プログラムは「宣言」を記述する**[[ヘッダファイル]]** (`.h`) と、「実装」を記述する**[[ソースファイル]]** (`.cpp`) に分割することで、保守性や再利用性が向上します。 + * **[[インクルードガード]]**: [[ヘッダファイル]]の多重インクルードによる再定義エラーを防ぐために、`#pragma once` や `#ifndef`/`#define`/`#endif` を使用します。 * **ビルドシステム**: 複数のファイルをコンパイル・リンクするプロセスを自動化するために、`make` や `CMake` といったツールが使われます。特に **CMake** はクロスプラットフォーム開発におけるデファクトスタンダードです。 diff --git a/public/docs/cpp/7-classes-advanced/3-0-static-member.md b/public/docs/cpp/7-classes-advanced/3-0-static-member.md index 014979b5..f06ae5d2 100644 --- a/public/docs/cpp/7-classes-advanced/3-0-static-member.md +++ b/public/docs/cpp/7-classes-advanced/3-0-static-member.md @@ -16,7 +16,7 @@ question: `static` キーワードを付けて宣言されたメンバ変数は、特定のオブジェクトに属さず、クラスそのものに属します。そのため、全オブジェクトでただ1つの実体を共有します。これを**クラス変数**と呼ぶこともあります。 * **宣言**: クラス定義の中で `static` を付けて行います。 - * **定義**: クラス定義の外(ソースファイル)で、メモリ上の実体を確保し、初期化します。 + * **定義**: クラス定義の外([[ソースファイル]])で、メモリ上の実体を確保し、初期化します。 `static` キーワードを付けて宣言されたメンバ関数は、特定のオブジェクトに依存せずに呼び出せます。そのため、`this` ポインタ(後述)を持ちません。 From 1c04b18c6f6cfaabd1b67e50de639118a11be5e4 Mon Sep 17 00:00:00 2001 From: na-trium-144 <100704180+na-trium-144@users.noreply.github.com> Date: Wed, 12 Aug 2026 00:08:19 +0900 Subject: [PATCH 7/9] c++ 6 --- .../docs/cpp/10-stl-containers/5-0-summary.md | 2 +- public/docs/cpp/11-stl-algorithms/1-0-about.md | 6 +++--- .../docs/cpp/11-stl-algorithms/4-0-summary.md | 2 +- .../cpp/12-raii-smart-ptrs/1-0-trycatch.md | 2 +- public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md | 8 ++++---- .../cpp/12-raii-smart-ptrs/3-1-uniqueptr.md | 6 +++--- .../cpp/12-raii-smart-ptrs/3-2-sharedptr.md | 6 +++--- .../docs/cpp/12-raii-smart-ptrs/4-0-summary.md | 6 +++--- .../cpp/12-raii-smart-ptrs/4-1-practice1.md | 6 +++--- .../cpp/12-raii-smart-ptrs/4-2-practice2.md | 6 +++--- public/docs/cpp/2-data-containers/-intro.md | 2 +- public/docs/cpp/3-pointers/4-4-memory-leak.md | 2 +- .../docs/cpp/4-functions/2-1-arg-by-value.md | 2 +- .../4-functions/2-4-arg-by-const-reference.md | 2 +- public/docs/cpp/4-functions/4-0-summary.md | 2 +- .../5-project-build/1-0-header-and-source.md | 4 ++-- .../cpp/5-project-build/2-0-include-guard.md | 2 +- .../docs/cpp/5-project-build/4-1-practice1.md | 6 +++--- public/docs/cpp/6-classes-basics/-intro.md | 2 +- public/docs/cpp/6-classes-basics/1-0-about.md | 9 ++++++++- .../docs/cpp/6-classes-basics/2-0-instance.md | 8 ++++++-- .../cpp/6-classes-basics/3-0-access-control.md | 18 +++++++++++------- .../4-0-constructor-destructor.md | 2 +- .../cpp/6-classes-basics/4-1-constructor.md | 10 ++++++---- .../cpp/6-classes-basics/4-2-destructor.md | 10 ++++++---- .../docs/cpp/6-classes-basics/5-0-summary.md | 14 +++++++------- .../docs/cpp/6-classes-basics/5-1-practice1.md | 10 +++++----- .../docs/cpp/6-classes-basics/5-2-practice2.md | 10 +++++----- public/docs/cpp/7-classes-advanced/-intro.md | 2 +- public/docs/cpp/7-classes-advanced/1-0-copy.md | 4 ++-- .../cpp/7-classes-advanced/1-1-shallow-copy.md | 6 +++--- .../cpp/7-classes-advanced/1-2-deep-copy.md | 8 ++++---- .../2-0-operator-overload.md | 15 ++++++++------- .../7-classes-advanced/3-0-static-member.md | 12 ++++++------ public/docs/cpp/7-classes-advanced/4-0-this.md | 10 +++++----- .../docs/cpp/7-classes-advanced/5-0-summary.md | 10 +++++----- .../cpp/7-classes-advanced/5-1-practice1.md | 4 ++-- .../cpp/7-classes-advanced/5-2-practice2.md | 4 ++-- .../docs/cpp/8-inheritance/1-0-inheritance.md | 8 ++++---- .../docs/cpp/8-inheritance/2-0-polymorphism.md | 4 ++-- .../cpp/8-inheritance/4-0-abstract-class.md | 8 ++++---- public/docs/cpp/8-inheritance/5-0-summary.md | 6 +++--- public/docs/cpp/8-inheritance/5-1-practice1.md | 4 ++-- public/docs/cpp/8-inheritance/5-2-practice2.md | 4 ++-- public/docs/cpp/9-templates/-intro.md | 2 +- .../docs/cpp/9-templates/2-0-class-template.md | 2 +- .../9-templates/2-1-class-template-detail.md | 6 +++--- public/docs/cpp/9-templates/3-0-summary.md | 2 +- public/docs/cpp/9-templates/3-2-practice2.md | 2 +- 49 files changed, 154 insertions(+), 134 deletions(-) diff --git a/public/docs/cpp/10-stl-containers/5-0-summary.md b/public/docs/cpp/10-stl-containers/5-0-summary.md index b57732db..35567ffd 100644 --- a/public/docs/cpp/10-stl-containers/5-0-summary.md +++ b/public/docs/cpp/10-stl-containers/5-0-summary.md @@ -8,7 +8,7 @@ question: [] ## この章のまとめ * **STL**は、**コンテナ**、**アルゴリズム**、**イテレータ**の3つの主要コンポーネントから構成される、C++の強力な標準ライブラリです。 - * **コンテナ**は、データを格納するためのクラスです。 + * **コンテナ**は、データを格納するための[[クラス]]です。 * `std::vector`は、最も一般的に使われる動的配列で、高速なランダムアクセスと末尾への簡単な要素追加が特徴です。 * `std::map`は、キーと値のペアを管理する連想配列で、キーによる高速な検索が可能です。 * 他にも`std::list`, `std::set`など、特定の用途に合わせた様々なコンテナが用意されています。 diff --git a/public/docs/cpp/11-stl-algorithms/1-0-about.md b/public/docs/cpp/11-stl-algorithms/1-0-about.md index 9a70c448..a20e3011 100644 --- a/public/docs/cpp/11-stl-algorithms/1-0-about.md +++ b/public/docs/cpp/11-stl-algorithms/1-0-about.md @@ -16,9 +16,9 @@ question: アルゴリズムは、特定のコンテナ([[`std::vector`]] や `std::list` など)に直接依存しないように設計されています。では、どうやってコンテナ内の要素にアクセスするのでしょうか?そこで登場するのが**イテレータ (Iterator)** です。 -イテレータは、コンテナ内の要素を指し示す「[[ポインタ]]のような」オブジェクトです。[[ポインタ]]のように `*` で要素の値を参照したり、`++` で次の要素に進んだりできます。 +イテレータは、コンテナ内の要素を指し示す「[[ポインタ]]のような」[[オブジェクト]]です。[[ポインタ]]のように `*` で要素の値を参照したり、`++` で次の要素に進んだりできます。 -ほとんどのコンテナは、以下の2つの重要なイテレータを取得するメンバ関数を持っています。 +ほとんどのコンテナは、以下の2つの重要なイテレータを取得する[[メンバ関数]]を持っています。 * `begin()`: コンテナの先頭要素を指すイテレータを返す。 * `end()`: コンテナの**最後の要素の次**を指すイテレータを返す。これは有効な要素を指していない「番兵」のような役割を果たします。 @@ -26,7 +26,7 @@ question: アルゴリズムは、この `begin()` と `end()` から得られるイテレータのペアを使い、操作対象の「範囲」を指定します。範囲は半開区間 `[begin, end)` で表され、`begin` が指す要素は範囲に含まれ、`end` が指す要素は含まれません。 > [!TIP] -> [[範囲ベース for ループ]] では内部でイテレータが使われており、 [[`std::vector`]] などに限らずイテレータが取得できるオブジェクトに対して使用できます。 +> [[範囲ベース for ループ]] では内部でイテレータが使われており、 [[`std::vector`]] などに限らずイテレータが取得できる[[オブジェクト]]に対して使用できます。 簡単な例を見てみましょう。イテレータを使って [[`std::vector`]] の全要素を表示するコードです。 このように、イテレータはコンテナの種類を問わず、統一的な方法で要素にアクセスする仕組みを提供します。これが、アルゴリズムが様々なコンテナに対して汎用的に機能する理由です。 diff --git a/public/docs/cpp/11-stl-algorithms/4-0-summary.md b/public/docs/cpp/11-stl-algorithms/4-0-summary.md index 85c5addc..c3bd086a 100644 --- a/public/docs/cpp/11-stl-algorithms/4-0-summary.md +++ b/public/docs/cpp/11-stl-algorithms/4-0-summary.md @@ -9,7 +9,7 @@ question: [] この章では、STLのアルゴリズムとラムダ式について学びました。 - * **イテレータ**は、コンテナの要素を指し示すオブジェクトであり、アルゴリズムとコンテナの間のインターフェースとして機能します。 + * **イテレータ**は、コンテナの要素を指し示す[[オブジェクト]]であり、アルゴリズムとコンテナの間のインターフェースとして機能します。 * `` ヘッダには、**`std::sort`** (ソート)、**`std::find`** (検索)、**`std::for_each`** (繰り返し処理) といった、汎用的で強力なアルゴリズムが多数用意されています。 * **ラムダ式**は、その場で定義できる無名関数であり、アルゴリズムに渡す処理を簡潔かつ直感的に記述することができます。 * **キャプチャ**機能を使うことで、ラムダ式の外にある変数を取り込んで処理に利用できます。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/1-0-trycatch.md b/public/docs/cpp/12-raii-smart-ptrs/1-0-trycatch.md index cca25a58..5f723a1d 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/1-0-trycatch.md +++ b/public/docs/cpp/12-raii-smart-ptrs/1-0-trycatch.md @@ -18,7 +18,7 @@ question: 例外処理は、以下の3つのキーワードで構成されます。 - * `throw`: 例外的な状況が発生したことを知らせるために、例外オブジェクトを「投げる」。 + * `throw`: 例外的な状況が発生したことを知らせるために、例外[[オブジェクト]]を「投げる」。 * `try`: 例外が発生する可能性のあるコードブロックを囲む。 * `catch`: `try` ブロック内で投げられた例外を「捕まえて」処理する。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md b/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md index 87b9c8f1..9583cd47 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md +++ b/public/docs/cpp/12-raii-smart-ptrs/2-0-raii.md @@ -12,11 +12,11 @@ question: ## RAIIイディオム -**RAII (Resource Acquisition Is Initialization)** は、「リソースの確保は、オブジェクトの初期化時に行い、リソースの解放は、オブジェクトの破棄時に行う」という設計パターンです。日本語では「リソース取得は初期化である」と訳されます。 +**RAII (Resource Acquisition Is Initialization)** は、「リソースの確保は、[[オブジェクト]]の初期化時に行い、リソースの解放は、[[オブジェクト]]の破棄時に行う」という設計パターンです。日本語では「リソース取得は初期化である」と訳されます。 -C++では、オブジェクトがそのスコープ([[変数]]が宣言された `{}` の範囲)を抜けるときに、そのオブジェクトの**デストラクタ**が自動的に呼び出されます。この仕組みは、関数が正常に終了した場合だけでなく、**例外が投げられてスコープを抜ける場合でも保証されています**。 +C++では、[[オブジェクト]]がそのスコープ([[変数]]が宣言された `{}` の範囲)を抜けるときに、その[[オブジェクト]]の**[[デストラクタ]]**が自動的に呼び出されます。この仕組みは、関数が正常に終了した場合だけでなく、**例外が投げられてスコープを抜ける場合でも保証されています**。 -RAIIはこの性質を利用して、リソースの解放処理をデストラクタに記述することで、リソースの解放を自動化し、[[`delete`]] の呼び忘れや例外発生時のリソースリークを防ぎます。 +RAIIはこの性質を利用して、リソースの解放処理を[[デストラクタ]]に記述することで、リソースの解放を自動化し、[[`delete`]] の呼び忘れや例外発生時のリソースリークを防ぎます。 簡単なRAIIクラスの例を見てみましょう。 @@ -65,6 +65,6 @@ Resource released. Exiting main. ``` -`use_resource` 関数が終了すると、`rw` オブジェクトがスコープを抜けるため、`ResourceWrapper` のデストラクタが自動的に呼び出され、`delete[]` が実行されます。もし `use_resource` の中で例外が発生したとしても、デストラクタは保証付きで呼び出されます。 +`use_resource` 関数が終了すると、`rw` [[オブジェクト]]がスコープを抜けるため、`ResourceWrapper` の[[デストラクタ]]が自動的に呼び出され、`delete[]` が実行されます。もし `use_resource` の中で例外が発生したとしても、[[デストラクタ]]は保証付きで呼び出されます。 この強力なRAIIイディオムを、動的メモリ管理のために標準ライブラリが提供してくれているのが**スマートポインタ**です。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/3-1-uniqueptr.md b/public/docs/cpp/12-raii-smart-ptrs/3-1-uniqueptr.md index ffb82967..e8d1de3a 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/3-1-uniqueptr.md +++ b/public/docs/cpp/12-raii-smart-ptrs/3-1-uniqueptr.md @@ -13,9 +13,9 @@ question: ### `std::unique_ptr` -`std::unique_ptr` は、管理するオブジェクトの**所有権を唯一に保つ**スマートポインタです。つまり、あるオブジェクトを指す `unique_ptr` は、常に一つしか存在できません。 +`std::unique_ptr` は、管理する[[オブジェクト]]の**所有権を唯一に保つ**スマートポインタです。つまり、ある[[オブジェクト]]を指す `unique_ptr` は、常に一つしか存在できません。 - * **唯一の所有権**: コピーが禁止されています。オブジェクトの所有権を別の `unique_ptr` に移したい場合は、**ムーブ (`std::move`)** を使います。 + * **唯一の所有権**: コピーが禁止されています。[[オブジェクト]]の所有権を別の `unique_ptr` に移したい場合は、**ムーブ (`std::move`)** を使います。 * **軽量**: ポインタ一つ分のサイズしかなく、オーバーヘッドが非常に小さいです。 `unique_ptr` を作成するには、`std::make_unique` を使うのが安全で推奨されています。 @@ -91,4 +91,4 @@ Returned from process_ptr Program finished. ``` -`unique_ptr` は、オブジェクトの所有者が誰であるかが明確な場合に最適です。基本的にはまず `unique_ptr` を使うことを検討しましょう。 +`unique_ptr` は、[[オブジェクト]]の所有者が誰であるかが明確な場合に最適です。基本的にはまず `unique_ptr` を使うことを検討しましょう。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/3-2-sharedptr.md b/public/docs/cpp/12-raii-smart-ptrs/3-2-sharedptr.md index b42d6093..52aaa84e 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/3-2-sharedptr.md +++ b/public/docs/cpp/12-raii-smart-ptrs/3-2-sharedptr.md @@ -13,10 +13,10 @@ question: ### `std::shared_ptr` -`std::shared_ptr` は、管理するオブジェクトの**所有権を複数のポインタで共有できる**スマートポインタです。 +`std::shared_ptr` は、管理する[[オブジェクト]]の**所有権を複数のポインタで共有できる**スマートポインタです。 * **共有された所有権**: `shared_ptr` は自由にコピーできます。コピーされるたびに、内部の**参照カウンタ**が増加します。 - * **自動解放**: `shared_ptr` が破棄される(デストラクタが呼ばれる)と参照カウンタが減少し、**参照カウンタが0になったとき**に、管理しているオブジェクトが解放([[`delete`]])されます。 + * **自動解放**: `shared_ptr` が破棄される([[デストラクタ]]が呼ばれる)と参照カウンタが減少し、**参照カウンタが0になったとき**に、管理している[[オブジェクト]]が解放([[`delete`]])されます。 * **オーバーヘッド**: 参照カウンタを管理するための追加のメモリと処理が必要なため、`unique_ptr` よりもわずかにオーバーヘッドが大きいです。 `shared_ptr` を作成するには、`std::make_shared` を使うのが効率的で安全です。 @@ -86,4 +86,4 @@ MyResource destructor Program finished. ``` -`shared_ptr` は、オブジェクトの寿命が単一のスコープや所有者に縛られず、複数のオブジェクトから共有される必要がある場合に便利です。ただし、所有権の関係が複雑になりがちなので、本当に共有が必要な場面に限定して使いましょう。 +`shared_ptr` は、[[オブジェクト]]の寿命が単一のスコープや所有者に縛られず、複数の[[オブジェクト]]から共有される必要がある場合に便利です。ただし、所有権の関係が複雑になりがちなので、本当に共有が必要な場面に限定して使いましょう。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/4-0-summary.md b/public/docs/cpp/12-raii-smart-ptrs/4-0-summary.md index 6ad99463..d2dace26 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/4-0-summary.md +++ b/public/docs/cpp/12-raii-smart-ptrs/4-0-summary.md @@ -10,9 +10,9 @@ question: * **例外処理**は `try`, `catch`, `throw` を使い、エラーが発生してもプログラムを安全に継続させるための仕組みです。 * 手動のメモリ管理下で例外が発生すると、**リソースリーク**を引き起こす危険があります。 - * **RAIIイディオム**は、リソースの確保をコンストラクタ、解放をデストラクタで行うことで、リソース管理を自動化するC++の重要な設計思想です。 + * **RAIIイディオム**は、リソースの確保を[[コンストラクタ]]、解放を[[デストラクタ]]で行うことで、リソース管理を自動化するC++の重要な設計思想です。 * **スマートポインタ**はRAIIを動的メモリ管理に適用したもので、[[`new`]] と [[`delete`]] の手動管理を不要にします。 - * **`std::unique_ptr`** はオブジェクトの**唯一の所有権**を管理します。軽量であり、所有権が明確な場合に第一の選択肢となります。 - * **`std::shared_ptr`** はオブジェクトの**所有権を共有**します。参照カウントによって管理され、最後の所有者がいなくなったときにオブジェクトを解放します。 + * **`std::unique_ptr`** は[[オブジェクト]]の**唯一の所有権**を管理します。軽量であり、所有権が明確な場合に第一の選択肢となります。 + * **`std::shared_ptr`** は[[オブジェクト]]の**所有権を共有**します。参照カウントによって管理され、最後の所有者がいなくなったときに[[オブジェクト]]を解放します。 モダンC++プログラミングでは、[[`new`]] と [[`delete`]] を直接書くことは極力避け、RAIIとスマートポインタを全面的に活用することが、安全でメンテナンス性の高いコードへの第一歩です。 diff --git a/public/docs/cpp/12-raii-smart-ptrs/4-1-practice1.md b/public/docs/cpp/12-raii-smart-ptrs/4-1-practice1.md index 77311629..ead9dec5 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/4-1-practice1.md +++ b/public/docs/cpp/12-raii-smart-ptrs/4-1-practice1.md @@ -9,11 +9,11 @@ question: ### 練習問題1: `unique_ptr` と所有権の移動 -`Employee` という名前のクラスを作成してください。このクラスは、コンストラクタで社員名を受け取って表示し、デストラクタで「(社員名) is leaving.」というメッセージを表示します。 +`Employee` という名前の[[クラス]]を作成してください。このクラスは、[[コンストラクタ]]で社員名を受け取って表示し、[[デストラクタ]]で「(社員名) is leaving.」というメッセージを表示します。 -[[`main` 関数]]で、`"Alice"` という名前の `Employee` オブジェクトを `std::make_unique` で作成し、その `unique_ptr` を `promote_employee` という関数に渡してください。`promote_employee` 関数は `unique_ptr` を引数として受け取り(所有権が移動します)、「(社員名) has been promoted\!」というメッセージを表示します。 +[[`main` 関数]]で、`"Alice"` という名前の `Employee` [[オブジェクト]]を `std::make_unique` で作成し、その `unique_ptr` を `promote_employee` という関数に渡してください。`promote_employee` 関数は `unique_ptr` を引数として受け取り(所有権が移動します)、「(社員名) has been promoted\!」というメッセージを表示します。 -プログラムを実行し、コンストラクタとデストラクタのメッセージが期待通りに表示されることを確認してください。 +プログラムを実行し、[[コンストラクタ]]と[[デストラクタ]]のメッセージが期待通りに表示されることを確認してください。 ```cpp:practice13_1.cpp #include diff --git a/public/docs/cpp/12-raii-smart-ptrs/4-2-practice2.md b/public/docs/cpp/12-raii-smart-ptrs/4-2-practice2.md index d104a2eb..2338faa9 100644 --- a/public/docs/cpp/12-raii-smart-ptrs/4-2-practice2.md +++ b/public/docs/cpp/12-raii-smart-ptrs/4-2-practice2.md @@ -9,13 +9,13 @@ question: ### 問題2: `shared_ptr` と所有権の共有 -`Project` という名前のクラスを作成してください。コンストラクタでプロジェクト名を受け取り、デストラクタで「Project (プロジェクト名) is finished.」と表示します。 +`Project` という名前の[[クラス]]を作成してください。[[コンストラクタ]]でプロジェクト名を受け取り、[[デストラクタ]]で「Project (プロジェクト名) is finished.」と表示します。 -[[`main` 関数]]で、`"Project Phoenix"` という名前の `Project` オブジェクトを `std::make_shared` で作成してください。 +[[`main` 関数]]で、`"Project Phoenix"` という名前の `Project` [[オブジェクト]]を `std::make_shared` で作成してください。 次に、`std::vector>` を作成し、作成した `shared_ptr` を2回 `push_back` してください。 その後、`shared_ptr` の参照カウント (`use_count()`) を表示してください。 最後に、`vector` を `clear()` して、再度参照カウントを表示してください。 -プログラムの実行が終了するときに `Project` のデストラクタが呼ばれることを確認してください。 +プログラムの実行が終了するときに `Project` の[[デストラクタ]]が呼ばれることを確認してください。 ```cpp:practice13_2.cpp #include diff --git a/public/docs/cpp/2-data-containers/-intro.md b/public/docs/cpp/2-data-containers/-intro.md index a42fb7fb..76797d4d 100644 --- a/public/docs/cpp/2-data-containers/-intro.md +++ b/public/docs/cpp/2-data-containers/-intro.md @@ -1,3 +1,3 @@ -他の言語(Python, JavaScript, C\#など)経験者がC++を学び始めるとき、最も躓きやすいのが「文字や配列の扱い」です。古いC言語の教科書では、[[ポインタ]]操作やメモリ管理が必須となる「Cスタイル」のやり方から入ることが多いのですが、**現代の実務的なC++(モダンC++)では、もっと安全で便利な「クラス(コンテナ)」を使います。** +他の言語(Python, JavaScript, C\#など)経験者がC++を学び始めるとき、最も躓きやすいのが「文字や配列の扱い」です。古いC言語の教科書では、[[ポインタ]]操作やメモリ管理が必須となる「Cスタイル」のやり方から入ることが多いのですが、**現代の実務的なC++(モダンC++)では、もっと安全で便利な「[[クラス]](コンテナ)」を使います。** この章では、ポインタの複雑な話を抜きにして、他の高級言語と同じくらい直感的にデータを扱えるツールを紹介します。 diff --git a/public/docs/cpp/3-pointers/4-4-memory-leak.md b/public/docs/cpp/3-pointers/4-4-memory-leak.md index d7ea5361..796b6c2b 100644 --- a/public/docs/cpp/3-pointers/4-4-memory-leak.md +++ b/public/docs/cpp/3-pointers/4-4-memory-leak.md @@ -21,6 +21,6 @@ term: > [[`std::vector`]] や [[`std::string`]] は、内部で [[`new`]] と [[`delete`]] を自動的に行ってくれています。 * 作成時に [[`new`]] で確保。 - * スコープを抜けるときに自動で [[`delete`]](デストラクタ)。 + * スコープを抜けるときに自動で [[`delete`]]([[デストラクタ]])。 これがC++のクラスの強力な機能(RAII)です。生の `new/delete` を直接使うことは、モダンC++では「最後の手段」あるいは「ライブラリを作る側の仕事」と考えられています。 diff --git a/public/docs/cpp/4-functions/2-1-arg-by-value.md b/public/docs/cpp/4-functions/2-1-arg-by-value.md index 76274aa7..5ddb2366 100644 --- a/public/docs/cpp/4-functions/2-1-arg-by-value.md +++ b/public/docs/cpp/4-functions/2-1-arg-by-value.md @@ -15,7 +15,7 @@ term: 特に何も指定しない場合のデフォルトです。[[変数]]の**コピー**が作成され、関数に渡されます。 * **メリット:** 安全。関数内で値を変更しても、呼び出し元の[[変数]]には影響しない。 - * **デメリット:** コストが高い。巨大な配列やオブジェクトを渡す際、丸ごとコピーするためメモリと時間を浪費する。 + * **デメリット:** コストが高い。巨大な配列や[[オブジェクト]]を渡す際、丸ごとコピーするためメモリと時間を浪費する。 > [!TIP] > `int` や `double` などの[[基本型]] → **値渡し** でOK。 diff --git a/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md b/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md index 1276748d..d1140fc6 100644 --- a/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md +++ b/public/docs/cpp/4-functions/2-4-arg-by-const-reference.md @@ -15,7 +15,7 @@ term: これが**C++で最も頻繁に使われるパターン**です。「コピーはしたくない(重いから)。でも、関数内で書き換えられたくもない」という要求を満たします。 * **構文:** `const 型& 引数名` - * **用途:** [[`std::string`]]、[[`std::vector`]]、クラスのオブジェクトなど、サイズが大きくなる可能性があるデータ。 + * **用途:** [[`std::string`]]、[[`std::vector`]]、[[クラス]]の[[オブジェクト]]など、サイズが大きくなる可能性があるデータ。 diff --git a/public/docs/cpp/4-functions/4-0-summary.md b/public/docs/cpp/4-functions/4-0-summary.md index b053f1a6..eaca0736 100644 --- a/public/docs/cpp/4-functions/4-0-summary.md +++ b/public/docs/cpp/4-functions/4-0-summary.md @@ -8,7 +8,7 @@ question: [] ## この章のまとめ * **[[プロトタイプ宣言]]**を使うことで、関数の定義順序に依存せずに記述できる。 - * **[[値渡し]]**は安全だが、大きなオブジェクトではコピーコストがかかる。 + * **[[値渡し]]**は安全だが、大きな[[オブジェクト]]ではコピーコストがかかる。 * **[[参照渡し]] (`&`)** は、[[ポインタ]]のような効率性を持ちながら、[[変数]]のエイリアスとして直感的に扱える。 * **[[`const` 参照渡し]] (`const T&`)** は、大きなデータを「読み取り専用」で効率的に渡すC++の定石である。 * **[[オーバーロード]]**により、同じ名前で異なる引数を受け取る関数を作れる。 diff --git a/public/docs/cpp/5-project-build/1-0-header-and-source.md b/public/docs/cpp/5-project-build/1-0-header-and-source.md index bb98798e..0e2d84d3 100644 --- a/public/docs/cpp/5-project-build/1-0-header-and-source.md +++ b/public/docs/cpp/5-project-build/1-0-header-and-source.md @@ -17,11 +17,11 @@ term: C++では、プログラムを**ヘッダファイル**と**ソースファイル**という2種類のファイルに分割するのが一般的です。 - * **ヘッダファイル (`.h` または `.hpp`)**: 「宣言」を置く場所です。クラスの定義、関数の[[プロトタイプ宣言]]、定数、テンプレートなどを記述します。他のファイルに対して「何ができるか(インターフェース)」を公開する役割を持ちます。 + * **ヘッダファイル (`.h` または `.hpp`)**: 「宣言」を置く場所です。[[クラス]]の定義、関数の[[プロトタイプ宣言]]、定数、テンプレートなどを記述します。他のファイルに対して「何ができるか(インターフェース)」を公開する役割を持ちます。 * **ソースファイル (`.cpp`)**: 「実装」を置く場所です。ヘッダファイルで宣言された関数の具体的な処理内容などを記述します。ヘッダファイルが公開したインターフェースを「どのように実現するか」を記述する役割を持ちます。 **なぜ分割するのか? 🤔** 1. **関心の分離**: インターフェース(何ができるか)と実装(どうやるか)を分離することで、コードの見通しが良くなります。他の開発者はヘッダファイルを見るだけで、その機能の使い方がわかります。 2. **コンパイル時間の短縮**: ソースファイルを変更した場合、再コンパイルはそのファイルだけで済みます。プロジェクト全体を再コンパイルする必要がないため、大規模なプロジェクトでは開発サイクルが劇的に速くなります。 -3. **再利用性の向上**: よく使う関数やクラスをまとめておけば、別のプロジェクトでそのファイルを[[インクルード]]するだけで簡単に再利用できます。 +3. **再利用性の向上**: よく使う関数や[[クラス]]をまとめておけば、別のプロジェクトでそのファイルを[[インクルード]]するだけで簡単に再利用できます。 diff --git a/public/docs/cpp/5-project-build/2-0-include-guard.md b/public/docs/cpp/5-project-build/2-0-include-guard.md index ebad9e70..122e6e84 100644 --- a/public/docs/cpp/5-project-build/2-0-include-guard.md +++ b/public/docs/cpp/5-project-build/2-0-include-guard.md @@ -14,7 +14,7 @@ term: 複数のファイルから同じ[[ヘッダファイル]]が[[インクルード]]される状況はよくあります。例えば、`A.h`が`B.h`を[[インクルード]]し、[[ソースファイル]]が`A.h`と`B.h`の両方をインクルードするような場合です。 -もし[[ヘッダファイル]]に何の対策もしていないと、同じ内容(クラス定義や関数宣言)が複数回読み込まれ、「再定義」としてコンパイルエラーが発生してしまいます。 +もし[[ヘッダファイル]]に何の対策もしていないと、同じ内容([[クラス]]定義や関数宣言)が複数回読み込まれ、「再定義」としてコンパイルエラーが発生してしまいます。 ```cpp:A.h #include "B.h" // B.hをインクルード diff --git a/public/docs/cpp/5-project-build/4-1-practice1.md b/public/docs/cpp/5-project-build/4-1-practice1.md index 15f3b791..92687ff7 100644 --- a/public/docs/cpp/5-project-build/4-1-practice1.md +++ b/public/docs/cpp/5-project-build/4-1-practice1.md @@ -9,11 +9,11 @@ question: ### 練習問題1: 電卓クラスの分割 -`Calculator` というクラスを作成してください。このクラスは、加算、減算、乗算、除算のメンバ関数を持ちます。 +`Calculator` という[[クラス]]を作成してください。このクラスは、加算、減算、乗算、除算の[[メンバ関数]]を持ちます。 * `Calculator.h`: `Calculator`クラスの定義を記述します。 -* `Calculator.cpp`: 各メンバ関数の実装を記述します。 -* `practice6_1.cpp`: `Calculator`クラスのインスタンスを作成し、いくつかの計算を行って結果を表示します。 +* `Calculator.cpp`: 各[[メンバ関数]]の実装を記述します。 +* `practice6_1.cpp`: `Calculator`クラスの[[インスタンス]]を作成し、いくつかの計算を行って結果を表示します。 これらのファイルをg++で手動ビルドして、プログラムを実行してください。 diff --git a/public/docs/cpp/6-classes-basics/-intro.md b/public/docs/cpp/6-classes-basics/-intro.md index 00eb3893..7de0837d 100644 --- a/public/docs/cpp/6-classes-basics/-intro.md +++ b/public/docs/cpp/6-classes-basics/-intro.md @@ -1 +1 @@ -これまでの章では、C++の基本的な文法やメモリの扱い方について学んできました。この章からは、C++の最も強力な機能の一つである**オブジェクト指向プログラミング (Object-Oriented Programming, OOP)** の世界に足を踏み入れます。OOPの考え方を身につけることで、より大規模で複雑なプログラムを、現実世界の「モノ」の概念に近い形で、直感的に設計・実装できるようになります。その第一歩として、OOPの中核をなす**クラス**の基礎を学びましょう。 +これまでの章では、C++の基本的な文法やメモリの扱い方について学んできました。この章からは、C++の最も強力な機能の一つである**オブジェクト指向プログラミング (Object-Oriented Programming, OOP)** の世界に足を踏み入れます。OOPの考え方を身につけることで、より大規模で複雑なプログラムを、現実世界の「モノ」の概念に近い形で、直感的に設計・実装できるようになります。その第一歩として、OOPの中核をなす**[[クラス]]**の基礎を学びましょう。 diff --git a/public/docs/cpp/6-classes-basics/1-0-about.md b/public/docs/cpp/6-classes-basics/1-0-about.md index 88653354..29a42309 100644 --- a/public/docs/cpp/6-classes-basics/1-0-about.md +++ b/public/docs/cpp/6-classes-basics/1-0-about.md @@ -7,6 +7,10 @@ question: - カプセル化とは、具体的にどのようなメリットがあるのでしょうか? - public:というキーワードはなぜ必要で、他に選択肢があるのでしょうか? - クラス定義の最後にセミコロン;が必要なのはなぜですか? +term: + - クラス + - メンバ変数 + - メンバ関数 --- ## クラスとは?: データ(メンバ変数)と処理(メンバ関数)のカプセル化 @@ -34,4 +38,7 @@ public: }; ``` -`class Person { ... };` という構文でクラスを定義します。クラス定義の最後にはセミコロン`;`が必要なので忘れないようにしましょう。現時点では、`public:`というキーワードは「これらのメンバは外部からアクセスできます」という意味だと考えておいてください。詳細は後ほど説明します。 +`class Person { ... };` という構文でクラスを定義します。 + +> [!IMPORTANT] +> クラス定義の最後にはセミコロン`;`が必要なので忘れないようにしましょう。 diff --git a/public/docs/cpp/6-classes-basics/2-0-instance.md b/public/docs/cpp/6-classes-basics/2-0-instance.md index 32715d4d..4e65f57e 100644 --- a/public/docs/cpp/6-classes-basics/2-0-instance.md +++ b/public/docs/cpp/6-classes-basics/2-0-instance.md @@ -6,11 +6,15 @@ question: - オブジェクトとインスタンスは同じものと考えていいですか?違いはありますか? - Person taro;でインスタンスを生成するとありますが、メモリ上では具体的に何が起きているのでしょうか? - ドット演算子.を使ってメンバにアクセスする理由は何ですか?他のアクセス方法もありますか? +term: + - インスタンス + - インスタンス化 + - オブジェクト --- ## インスタンスの生成: クラスからオブジェクトを作ってみる -クラスはあくまで「設計図」です。実際にプログラムで利用するためには、この設計図をもとに実体を作る必要があります。クラスから作られた実体のことを**オブジェクト (object)** または**インスタンス (instance)** と呼び、オブジェクトを作ることを**インスタンス化 (instantiation)** と言います。 +[[クラス]]はあくまで「設計図」です。実際にプログラムで利用するためには、この設計図をもとに実体を作る必要があります。[[クラス]]から作られた実体のことを**オブジェクト (object)** または**インスタンス (instance)** と呼び、オブジェクトを作ることを**インスタンス化 (instantiation)** と言います。 インスタンス化の構文は、[[変数]]の宣言とよく似ています。 @@ -55,4 +59,4 @@ My name is Taro, and I am 30 years old. My name is Hanako, and I am 25 years old. ``` -このように、`クラス名 インスタンス名;` という形でインスタンスを生成できます。インスタンスのメンバ変数やメンバ関数にアクセスするには、`インスタンス名.メンバ名` のように**ドット演算子 (`.`)** を使います。`taro`と`hanako`は同じ`Person`クラスから作られたインスタンスですが、それぞれが独立したデータを持っていることがわかります。 +このように、`クラス名 インスタンス名;` という形でインスタンスを生成できます。インスタンスの[[メンバ変数]]や[[メンバ関数]]にアクセスするには、`インスタンス名.メンバ名` のように**ドット演算子 (`.`)** を使います。`taro`と`hanako`は同じ`Person`[[クラス]]から作られたインスタンスですが、それぞれが独立したデータを持っていることがわかります。 diff --git a/public/docs/cpp/6-classes-basics/3-0-access-control.md b/public/docs/cpp/6-classes-basics/3-0-access-control.md index ef4a3f84..d4178e5f 100644 --- a/public/docs/cpp/6-classes-basics/3-0-access-control.md +++ b/public/docs/cpp/6-classes-basics/3-0-access-control.md @@ -7,11 +7,14 @@ question: - setName関数の引数にあるconst std::string& newNameのconstと&は何を意味しているのですか? - getName() constのconstは何のためにあるのですか? - 情報の隠蔽をすることの具体的なメリットは、不正な値の防止以外に何かありますか? +term: + - private + - public --- ## アクセス制御: public と private による情報の隠蔽 -先ほどの`Person`クラスの例では、[[`main`関数]]から`taro.age = 30;`のようにメンバ変数に直接アクセスできました。これは手軽ですが、問題を引き起こす可能性があります。例えば、年齢にマイナスの値や非現実的な値を設定できてしまうかもしれません。 +先ほどの`Person`[[クラス]]の例では、[[`main`関数]]から`taro.age = 30;`のように[[メンバ変数]]に直接アクセスできました。これは手軽ですが、問題を引き起こす可能性があります。例えば、年齢にマイナスの値や非現実的な値を設定できてしまうかもしれません。 ```cpp Person jiro; @@ -20,14 +23,14 @@ jiro.age = -5; // 本来ありえない値が設定できてしまう! jiro.introduce(); ``` -このような意図しない操作を防ぐために、C++には**アクセス制御**の仕組みがあります。クラスのメンバは、外部からのアクセスの可否を指定できます。 +このような意図しない操作を防ぐために、C++には**アクセス制御**の仕組みがあります。[[クラス]]のメンバは、外部からのアクセスの可否を指定できます。 - - **`public`**: クラスの外部([[`main`関数]]など)から自由にアクセスできます。 - - **`private`**: そのクラスのメンバ関数からしかアクセスできません。外部からはアクセス不可です。 + - **`public`**: [[クラス]]の外部([[`main`関数]]など)から自由にアクセスできます。 + - **`private`**: その[[クラス]]の[[メンバ関数]]からしかアクセスできません。外部からはアクセス不可です。 -アクセス制御の基本は、**メンバ変数は`private`にし、メンバ関数は`public`にする**ことです。これにより、データの不正な書き換えを防ぎ、クラスの内部実装を外部から隠蔽します。これを**情報の隠蔽 (information hiding)** と呼び、カプセル化の重要な目的の一つです。 +アクセス制御の基本は、**[[メンバ変数]]は`private`にし、[[メンバ関数]]は`public`にする**ことです。これにより、データの不正な書き換えを防ぎ、[[クラス]]の内部実装を外部から隠蔽します。これを**情報の隠蔽 (information hiding)** と呼び、カプセル化の重要な目的の一つです。 -`private`なメンバ変数に安全にアクセスするために、`public`なメンバ関数(**ゲッター**や**セッター**と呼ばれる)を用意するのが一般的です。 +`private`な[[メンバ変数]]に安全にアクセスするために、`public`な[[メンバ関数]](**ゲッター**や**セッター**と呼ばれる)を用意するのが一般的です。 ```cpp:access_control.cpp #include @@ -95,6 +98,7 @@ Error: Invalid age value. Name: Saburo ``` -`setAge`関数内で値の妥当性チェックを行っている点に注目してください。このように、クラスの利用者は内部の実装を気にすることなく、提供された`public`なインターフェース(メンバ関数)を通じて安全にオブジェクトを操作できます。 +`setAge`関数内で値の妥当性チェックを行っている点に注目してください。このように、[[クラス]]の利用者は内部の実装を気にすることなく、提供された`public`なインターフェース([[メンバ関数]])を通じて安全に[[オブジェクト]]を操作できます。 +> [!TIP] > `const`キーワード: `getName() const` のようにメンバ関数の後ろに`const`を付けると、その関数がメンバ変数を変更しないことをコンパイラに約束します。このような関数を**constメンバ関数**と呼びます。 diff --git a/public/docs/cpp/6-classes-basics/4-0-constructor-destructor.md b/public/docs/cpp/6-classes-basics/4-0-constructor-destructor.md index 21fe0e93..034b08eb 100644 --- a/public/docs/cpp/6-classes-basics/4-0-constructor-destructor.md +++ b/public/docs/cpp/6-classes-basics/4-0-constructor-destructor.md @@ -7,4 +7,4 @@ question: [] ## コンストラクタとデストラクタ: オブジェクトが生まれてから消えるまで -オブジェクトは生成され、利用され、やがて破棄されます。このライフサイクルに合わせて特別な処理を自動的に実行するための仕組みが**コンストラクタ**と**デストラクタ**です。 +[[オブジェクト]]は生成され、利用され、やがて破棄されます。このライフサイクルに合わせて特別な処理を自動的に実行するための仕組みが**コンストラクタ**と**デストラクタ**です。 diff --git a/public/docs/cpp/6-classes-basics/4-1-constructor.md b/public/docs/cpp/6-classes-basics/4-1-constructor.md index 7abefc38..64a26c37 100644 --- a/public/docs/cpp/6-classes-basics/4-1-constructor.md +++ b/public/docs/cpp/6-classes-basics/4-1-constructor.md @@ -7,18 +7,22 @@ question: - コンストラクタの関数名がクラス名と同じで、戻り値の型を指定しないのはなぜですか? - コンストラクタを複数定義できる(オーバーロード)とは、具体的にどのような場合に使いますか? - 初期化忘れを防ぐというメリットは、どのような状況で特に役立ちますか? +term: + - コンストラクタ --- ### コンストラクタ (Constructor) -**コンストラクタ**は、インスタンスが生成されるときに**自動的に呼び出される**特別なメンバ関数です。主な役割は、メンバ変数の初期化です。 +**コンストラクタ**は、[[インスタンス]]が生成されるときに**自動的に呼び出される**特別な[[メンバ関数]]です。主な役割は、[[メンバ変数]]の初期化です。 コンストラクタには以下の特徴があります。 - - 関数名がクラス名と全く同じ。 + - 関数名が[[クラス]]名と全く同じ。 - 戻り値の型を指定しない([[`void`]]も付けない)。 - 引数を取ることができ、複数定義できる([[オーバーロード]])。 +以下の例のように、[[インスタンス]]生成時に`()`で初期値を渡すことで、[[オブジェクト]]を生成と同時に有効な状態にできます。`set`関数を別途呼び出す手間が省け、初期化忘れを防ぐことができます。 + ```cpp:constructor.cpp class Person { private: @@ -46,5 +50,3 @@ int main() { Constructor called for Yuko My name is Yuko, and I am 22 years old. ``` - -このように、インスタンス生成時に`()`で初期値を渡すことで、オブジェクトを生成と同時に有効な状態にできます。`set`関数を別途呼び出す手間が省け、初期化忘れを防ぐことができます。 diff --git a/public/docs/cpp/6-classes-basics/4-2-destructor.md b/public/docs/cpp/6-classes-basics/4-2-destructor.md index 1b049eb0..bdb3a74a 100644 --- a/public/docs/cpp/6-classes-basics/4-2-destructor.md +++ b/public/docs/cpp/6-classes-basics/4-2-destructor.md @@ -9,17 +9,19 @@ question: - デストラクタは1つのクラスに1つしか定義できないのはなぜですか? - オブジェクトが使用していたリソースの後片付けとは、具体的にどのようなことを指しますか? - RAII(Resource Acquisition Is Initialization)とは何ですか? +term: + - デストラクタ --- ### デストラクタ (Destructor) -**デストラクタ**は、インスタンスが破棄されるとき(例えば、変数のスコープを抜けるとき)に**自動的に呼び出される**特別なメンバ関数です。主な役割は、オブジェクトが使用していたリソース(メモリやファイルなど)の後片付けです。 +**デストラクタ**は、[[インスタンス]]が破棄されるとき(例えば、変数のスコープを抜けるとき)に**自動的に呼び出される**特別な[[メンバ関数]]です。主な役割は、[[オブジェクト]]が使用していたリソース(メモリやファイルなど)の後片付けです。 デストラクタには以下の特徴があります。 - - 関数名が `~` + クラス名。 + - 関数名が `~` + [[クラス]]名。 - 戻り値も引数も取らない。 - - 1つのクラスに1つしか定義できない。 + - 1つの[[クラス]]に1つしか定義できない。 ```cpp:constructor_destructor.cpp #include @@ -73,4 +75,4 @@ Destructor called for Kenji. --- Back in main --- ``` -実行結果を見ると、`kenji`オブジェクトが生成されたときにコンストラクタが、`create_person_scope`関数のスコープを抜けるときにデストラクタが自動的に呼び出されていることがわかります。動的に確保したメモリの解放など、クリーンアップ処理はデストラクタに書くのが定石です。この考え方は、[[./12]]で学ぶRAII(Resource Acquisition Is Initialization)という重要な概念に繋がります。 +実行結果を見ると、`kenji`[[オブジェクト]]が生成されたときにコンストラクタが、`create_person_scope`関数のスコープを抜けるときにデストラクタが自動的に呼び出されていることがわかります。動的に確保したメモリの解放など、クリーンアップ処理はデストラクタに書くのが定石です。この考え方は、[[./12]]で学ぶRAII(Resource Acquisition Is Initialization)という重要な概念に繋がります。 diff --git a/public/docs/cpp/6-classes-basics/5-0-summary.md b/public/docs/cpp/6-classes-basics/5-0-summary.md index caeb7b8b..58b27b2d 100644 --- a/public/docs/cpp/6-classes-basics/5-0-summary.md +++ b/public/docs/cpp/6-classes-basics/5-0-summary.md @@ -7,13 +7,13 @@ question: [] ## この章のまとめ -この章では、C++におけるオブジェクト指向プログラミングの第一歩として、クラスの基本的な概念を学びました。 +この章では、C++におけるオブジェクト指向プログラミングの第一歩として、[[クラス]]の基本的な概念を学びました。 - - **クラス**は、データ(**メンバ変数**)と処理(**メンバ関数**)を一つにまとめた「設計図」です。 - - クラスから実体である**オブジェクト(インスタンス)**を生成して使用します。 + - **[[クラス]]**は、データ(**[[メンバ変数]]**)と処理(**[[メンバ関数]]**)を一つにまとめた「設計図」です。 + - クラスから実体である**[[オブジェクト]]([[インスタンス]])**を生成して使用します。 - **カプセル化**は、関連するデータと処理をまとめることです。 - - **アクセス制御**(`public`, `private`)により、外部からアクセスされたくないメンバを保護します(**情報の隠蔽**)。 - - **コンストラクタ**は、オブジェクト生成時に自動で呼ばれ、初期化を行います。 - - **デストラクタ**は、オブジェクト破棄時に自動で呼ばれ、後片付けを行います。 + - **アクセス制御**([[`public`]], [[`private`]])により、外部からアクセスされたくないメンバを保護します(**情報の隠蔽**)。 + - **[[コンストラクタ]]**は、[[オブジェクト]]生成時に自動で呼ばれ、初期化を行います。 + - **[[デストラクタ]]**は、[[オブジェクト]]破棄時に自動で呼ばれ、後片付けを行います。 -クラスを使いこなすことで、プログラムの部品化が進み、再利用性やメンテナンス性が格段に向上します。[[./next]]では、クラスのさらに進んだ機能について学んでいきましょう。 +[[クラス]]を使いこなすことで、プログラムの部品化が進み、再利用性やメンテナンス性が格段に向上します。[[./next]]では、クラスのさらに進んだ機能について学んでいきましょう。 diff --git a/public/docs/cpp/6-classes-basics/5-1-practice1.md b/public/docs/cpp/6-classes-basics/5-1-practice1.md index f1dda969..7e22bb1d 100644 --- a/public/docs/cpp/6-classes-basics/5-1-practice1.md +++ b/public/docs/cpp/6-classes-basics/5-1-practice1.md @@ -10,12 +10,12 @@ question: ### 練習問題1: 長方形クラス -幅(`width`)と高さ(`height`)をメンバ変数として持つ`Rectangle`クラスを作成してください。 +幅(`width`)と高さ(`height`)を[[メンバ変数]]として持つ`Rectangle`[[クラス]]を作成してください。 - - メンバ変数は`private`で定義してください。 - - コンストラクタで幅と高さを初期化できるようにしてください。 - - 面積を計算して返す`getArea()`メソッドと、周の長さを計算して返す`getPerimeter()`メソッドを`public`で実装してください。 - - [[`main`関数]]で`Rectangle`クラスのインスタンスをいくつか生成し、面積と周の長さを表示するプログラムを作成してください。 + - [[メンバ変数]]は[[`private`]]で定義してください。 + - [[コンストラクタ]]で幅と高さを初期化できるようにしてください。 + - 面積を計算して返す`getArea()`メソッドと、周の長さを計算して返す`getPerimeter()`メソッドを[[`public`]]で実装してください。 + - [[`main`関数]]で`Rectangle`クラスの[[インスタンス]]をいくつか生成し、面積と周の長さを表示するプログラムを作成してください。 ```cpp:practice7_1.cpp #include diff --git a/public/docs/cpp/6-classes-basics/5-2-practice2.md b/public/docs/cpp/6-classes-basics/5-2-practice2.md index e8f192bc..ae60da3f 100644 --- a/public/docs/cpp/6-classes-basics/5-2-practice2.md +++ b/public/docs/cpp/6-classes-basics/5-2-practice2.md @@ -10,12 +10,12 @@ question: ### 練習問題2: 書籍クラス -タイトル(`title`)、著者(`author`)、ページ数(`pages`)をメンバ変数として持つ`Book`クラスを作成してください。 +タイトル(`title`)、著者(`author`)、ページ数(`pages`)を[[メンバ変数]]として持つ`Book`[[クラス]]を作成してください。 - - メンバ変数は`private`で定義してください。 - - コンストラクタで、タイトル、著者、ページ数を初期化できるようにしてください。 - - 本の情報を整形してコンソールに出力する`printInfo()`メソッドを`public`で実装してください。(例: `Title: [タイトル], Author: [著者], Pages: [ページ数] pages`) - - [[`main`関数]]で`Book`クラスのインスタンスを生成し、その情報を表示してください。 + - [[メンバ変数]]は[[`private`]]で定義してください。 + - [[コンストラクタ]]で、タイトル、著者、ページ数を初期化できるようにしてください。 + - 本の情報を整形してコンソールに出力する`printInfo()`メソッドを[[`public`]]で実装してください。(例: `Title: [タイトル], Author: [著者], Pages: [ページ数] pages`) + - [[`main`関数]]で`Book`クラスの[[インスタンス]]を生成し、その情報を表示してください。 ```cpp:practice7_2.cpp #include diff --git a/public/docs/cpp/7-classes-advanced/-intro.md b/public/docs/cpp/7-classes-advanced/-intro.md index 46b1d270..e295d407 100644 --- a/public/docs/cpp/7-classes-advanced/-intro.md +++ b/public/docs/cpp/7-classes-advanced/-intro.md @@ -1 +1 @@ -[[./6]]では、C++のオブジェクト指向プログラミングの核となる`class`の基本的な使い方を学びました。しかし、クラスを真に強力なツールとして使いこなすには、もう少し知識が必要です。この章では、オブジェクトのコピー、演算子のオーバーロード、クラスで共有されるメンバなど、より実践的でパワフルな機能について掘り下げていきます。これらの概念をマスターすることで、あなたの書くクラスはより安全で、直感的で、再利用性の高いものになるでしょう。 +[[./6]]では、C++のオブジェクト指向プログラミングの核となる`class`の基本的な使い方を学びました。しかし、[[クラス]]を真に強力なツールとして使いこなすには、もう少し知識が必要です。この章では、[[オブジェクト]]のコピー、演算子のオーバーロード、クラスで共有されるメンバなど、より実践的でパワフルな機能について掘り下げていきます。これらの概念をマスターすることで、あなたの書くクラスはより安全で、直感的で、再利用性の高いものになるでしょう。 diff --git a/public/docs/cpp/7-classes-advanced/1-0-copy.md b/public/docs/cpp/7-classes-advanced/1-0-copy.md index 6a22e67f..93bc9bd2 100644 --- a/public/docs/cpp/7-classes-advanced/1-0-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-0-copy.md @@ -12,11 +12,11 @@ question: ## オブジェクトのコピー: コピーコンストラクタと代入演算子 -オブジェクトをコピーしたい場面は頻繁にあります。例えば、関数の引数にオブジェクトを渡すとき([[値渡し]])や、既存のオブジェクトで新しいオブジェクトを[[初期化]]するときなどです。 +[[オブジェクト]]をコピーしたい場面は頻繁にあります。例えば、関数の引数に[[オブジェクト]]を渡すとき([[値渡し]])や、既存の[[オブジェクト]]で新しい[[オブジェクト]]を[[初期化]]するときなどです。 ```cpp Vector2D v1(1.0, 2.0); Vector2D v2 = v1; // ここでコピーが発生! ``` -多くの場合、コンパイラが自動的に生成するコピー機能で十分です。しかし、クラスが[[ポインタ]]などでリソース(メモリなど)を管理している場合、単純なコピーでは問題が発生します。 +多くの場合、コンパイラが自動的に生成するコピー機能で十分です。しかし、[[クラス]]が[[ポインタ]]などでリソース(メモリなど)を管理している場合、単純なコピーでは問題が発生します。 diff --git a/public/docs/cpp/7-classes-advanced/1-1-shallow-copy.md b/public/docs/cpp/7-classes-advanced/1-1-shallow-copy.md index 4a2fa767..c882161e 100644 --- a/public/docs/cpp/7-classes-advanced/1-1-shallow-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-1-shallow-copy.md @@ -16,9 +16,9 @@ question: ### 何もしないとどうなる? (浅いコピー) まず、コピーの機能を自分で作らなかった場合に何が起きるか見てみましょう。 -コンパイラは、メンバ変数を単純にコピーするだけの「浅いコピー」を行います。 +コンパイラは、[[メンバ変数]]を単純にコピーするだけの「浅いコピー」を行います。 -ここでは、`int`への[[ポインタ]]を一つだけ持つ`ResourceHolder`(リソース保持者)というクラスを考えます。 +ここでは、`int`への[[ポインタ]]を一つだけ持つ`ResourceHolder`(リソース保持者)という[[クラス]]を考えます。 ```cpp:shallow_copy.cpp // 悪い例:浅いコピーの問題点 @@ -56,4 +56,4 @@ Resource 107521 destroyed. (at 0x1a4012b0) free(): double free detected in tcache 2 ``` -この例では、`r2`が作られるときに`r1`の[[ポインタ]]`m_data`の値(メモリアドレス)だけがコピーされます。その結果、2つのオブジェクトが1つのメモリ領域を指してしまいます。プログラム終了時にそれぞれのデストラクタが呼ばれ、同じメモリを2回解放しようとしてエラーになります。 +この例では、`r2`が作られるときに`r1`の[[ポインタ]]`m_data`の値(メモリアドレス)だけがコピーされます。その結果、2つの[[オブジェクト]]が1つのメモリ領域を指してしまいます。プログラム終了時にそれぞれの[[デストラクタ]]が呼ばれ、同じメモリを2回解放しようとしてエラーになります。 diff --git a/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md b/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md index 2300d02b..04f014fa 100644 --- a/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md @@ -122,11 +122,11 @@ Resource 10 destroyed. (at 0x139f065e0) *(メモリアドレスは実行するたびに変わります)* -実行結果を見ると、`rh1`, `rh2`, `rh3` はそれぞれ異なるメモリ[[アドレス]] (`Address`) を持っていることがわかります。これにより、各オブジェクトは独立したリソースを管理でき、プログラム終了時にそれぞれのデストラクタが安全にメモリを解放できます。 +実行結果を見ると、`rh1`, `rh2`, `rh3` はそれぞれ異なるメモリ[[アドレス]] (`Address`) を持っていることがわかります。これにより、各[[オブジェクト]]は独立したリソースを管理でき、プログラム終了時にそれぞれの[[デストラクタ]]が安全にメモリを解放できます。 | 機能 | いつ呼ばれるか | 何をするか | | :--- | :--- | :--- | -| **コピーコンストラクタ** | オブジェクトが**作られる時**に、他のオブジェクトで[[初期化]]される場合
`ResourceHolder r2 = r1;` | 新しいリソースを確保し、元のオブジェクトの**値**をコピーする。 | -| **コピー代入演算子** | **既にあるオブジェクト**に、他のオブジェクトを代入する場合
`r3 = r1;` | 1. 自分が持っている古いリソースを解放する。
2. 新しいリソースを確保し、元のオブジェクトの**値**をコピーする。 | +| **コピーコンストラクタ** | [[オブジェクト]]が**作られる時**に、他の[[オブジェクト]]で[[初期化]]される場合
`ResourceHolder r2 = r1;` | 新しいリソースを確保し、元の[[オブジェクト]]の**値**をコピーする。 | +| **コピー代入演算子** | **既にある[[オブジェクト]]**に、他の[[オブジェクト]]を代入する場合
`r3 = r1;` | 1. 自分が持っている古いリソースを解放する。
2. 新しいリソースを確保し、元の[[オブジェクト]]の**値**をコピーする。 | -このように、[[ポインタ]]でリソースを管理するクラスでは、安全なコピーを実現するためにこの2つの関数を自分で定義することが不可欠です。 +このように、[[ポインタ]]でリソースを管理する[[クラス]]では、安全なコピーを実現するためにこの2つの関数を自分で定義することが不可欠です。 diff --git a/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md b/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md index 8541c3ae..8ca61f3d 100644 --- a/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md +++ b/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md @@ -13,18 +13,21 @@ question: ## 演算子のオーバーロード -C++では、`+`, `-`, `==`, `<<` などの組み込み演算子を、自作のクラスで使えるように**再定義([[オーバーロード]])**できます。これにより、クラスのインスタンスをあたかも組み込み型(`int`や`double`など)のように直感的に扱えるようになります。 +C++では、`+`, `-`, `==`, `<<` などの組み込み演算子を、自作の[[クラス]]で使えるように**再定義([[オーバーロード]])**できます。これにより、[[クラス]]の[[インスタンス]]をあたかも[[基本型]](`int`や`double`など)のように直感的に扱えるようになります。 -例えば、2次元ベクトルを表す `Vector2D` クラスがあるとします。`v3 = v1 + v2;` のように、ベクトル同士の足し算を自然に記述できると便利ですよね。 +例えば、2次元ベクトルを表す `Vector2D` [[クラス]]があるとします。`v3 = v1 + v2;` のように、ベクトル同士の足し算を自然に記述できると便利ですよね。 -演算子のオーバーロードは、メンバ関数または非メンバ関数(グローバル関数)として定義します。 +演算子のオーバーロードは、[[メンバ関数]]または非メンバ関数(グローバル関数)として定義します。 -| 演算子 | メンバ関数での定義 | 非メンバ関数での定義 | +| 演算子 | [[メンバ関数]]での定義 | 非メンバ関数での定義 | | :--- | :--- | :--- | | 二項演算子 (`+`, `==` etc.) | `T operator+(const U& rhs);` | `T operator+(const T& lhs, const U& rhs);` | | 単項演算子 (`-`, `!` etc.) | `T operator-();` | `T operator-(const T& obj);` | -`Vector2D` クラスで `+`(加算)、`==`(等価比較)、`<<`(ストリーム出力)をオーバーロードしてみましょう。 +> [!WARNING] +> `operator<<` は、左辺のオペランドが `std::ostream` 型(`std::cout` など)であるため、`Vector2D` の[[メンバ関数]]としては定義できません。そのため、非メンバ関数として定義するのが一般的です。 + +`Vector2D` [[クラス]]で `+`(加算)、`==`(等価比較)、`<<`(ストリーム出力)をオーバーロードしてみましょう。 ```cpp:operator_overloading.cpp #include @@ -78,5 +81,3 @@ v2: (3, 4) v3 = v1 + v2: (4, 6) v1 is equal to (1.0, 2.0) ``` - -`operator<<` は、左辺のオペランドが `std::ostream` 型(`std::cout` など)であるため、`Vector2D` のメンバ関数としては定義できません。そのため、非メンバ関数として定義するのが一般的です。 diff --git a/public/docs/cpp/7-classes-advanced/3-0-static-member.md b/public/docs/cpp/7-classes-advanced/3-0-static-member.md index f06ae5d2..3bdee0f8 100644 --- a/public/docs/cpp/7-classes-advanced/3-0-static-member.md +++ b/public/docs/cpp/7-classes-advanced/3-0-static-member.md @@ -11,19 +11,19 @@ question: ## staticメンバ -通常、クラスのメンバ変数はオブジェクトごとに個別のメモリ領域を持ちます。しかし、あるクラスの**全てのオブジェクトで共有したい**情報もあります。例えば、「これまでに生成されたオブジェクトの総数」などです。このような場合、**staticメンバ**を使用します。 +通常、[[クラス]]の[[メンバ変数]]は[[オブジェクト]]ごとに個別のメモリ領域を持ちます。しかし、ある[[クラス]]の**全ての[[オブジェクト]]で共有したい**情報もあります。例えば、「これまでに生成された[[オブジェクト]]の総数」などです。このような場合、**staticメンバ**を使用します。 -`static` キーワードを付けて宣言されたメンバ変数は、特定のオブジェクトに属さず、クラスそのものに属します。そのため、全オブジェクトでただ1つの実体を共有します。これを**クラス変数**と呼ぶこともあります。 +`static` キーワードを付けて宣言された[[メンバ変数]]は、特定の[[オブジェクト]]に属さず、[[クラス]]そのものに属します。そのため、全[[オブジェクト]]でただ1つの実体を共有します。これを**クラス変数**と呼ぶこともあります。 * **宣言**: クラス定義の中で `static` を付けて行います。 * **定義**: クラス定義の外([[ソースファイル]])で、メモリ上の実体を確保し、初期化します。 -`static` キーワードを付けて宣言されたメンバ関数は、特定のオブジェクトに依存せずに呼び出せます。そのため、`this` ポインタ(後述)を持ちません。 +`static` キーワードを付けて宣言された[[メンバ関数]]は、特定の[[オブジェクト]]に依存せずに呼び出せます。そのため、`this` ポインタ(後述)を持ちません。 - * **アクセス**: staticメンバ変数や他のstaticメンバ関数にはアクセスできますが、非staticなメンバ(インスタンスごとのメンバ変数やメンバ関数)にはアクセスできません。 - * **呼び出し**: `クラス名::関数名()` のように、オブジェクトを生成しなくても呼び出せます。 + * **アクセス**: staticメンバ変数や他のstaticメンバ関数にはアクセスできますが、非staticなメンバ([[インスタンス]]ごとのメンバ変数やメンバ関数)にはアクセスできません。 + * **呼び出し**: `クラス名::関数名()` のように、[[オブジェクト]]を生成しなくても呼び出せます。 -ゲームに登場する `Player` クラスがあり、現在何人のプレイヤーが存在するかを管理する例を見てみましょう。 +ゲームに登場する `Player` [[クラス]]があり、現在何人のプレイヤーが存在するかを管理する例を見てみましょう。 ```cpp:static_members.cpp #include diff --git a/public/docs/cpp/7-classes-advanced/4-0-this.md b/public/docs/cpp/7-classes-advanced/4-0-this.md index 8cf0cd61..88e9da05 100644 --- a/public/docs/cpp/7-classes-advanced/4-0-this.md +++ b/public/docs/cpp/7-classes-advanced/4-0-this.md @@ -10,14 +10,14 @@ question: ## thisポインタ -非staticなメンバ関数が呼び出されるとき、その関数は「どのオブジェクトに対して呼び出されたか」を知る必要があります。コンパイラは、そのメンバ関数に対して、呼び出し元のオブジェクトの[[アドレス]]を暗黙的に渡します。このアドレスを保持するのが `this` ポインタです。 +非staticな[[メンバ関数]]が呼び出されるとき、その関数は「どの[[オブジェクト]]に対して呼び出されたか」を知る必要があります。コンパイラは、その[[メンバ関数]]に対して、呼び出し元の[[オブジェクト]]の[[アドレス]]を暗黙的に渡します。このアドレスを保持するのが `this` ポインタです。 -`this` は、メンバ関数内で使用できるキーワードで、自分自身のオブジェクトを指す[[ポインタ]]です。 +`this` は、[[メンバ関数]]内で使用できるキーワードで、自分自身の[[オブジェクト]]を指す[[ポインタ]]です。 `this` ポインタが主に使われるのは、以下のような場面です。 -1. **メンバ変数と引数の名前が同じ場合** - コンストラクタの初期化子リストを使わない場合など、引数名とメンバ変数名が同じになることがあります。その際、`this->` を付けることでメンバ変数であることを明示できます。 +1. **[[メンバ変数]]と引数の名前が同じ場合** + [[コンストラクタ]]の初期化子リストを使わない場合など、引数名と[[メンバ変数]]名が同じになることがあります。その際、`this->` を付けることで[[メンバ変数]]であることを明示できます。 ```cpp void setX(double x) { @@ -26,7 +26,7 @@ question: ``` 2. **自分自身の参照や[[ポインタ]]を返す場合** - コピー代入演算子で `return *this;` としたように、オブジェクト自身を返したい場合に使います。これにより、**メソッドチェーン**(`obj.setX(10).setY(20);` のような連続したメソッド呼び出し)が可能になります。 + コピー代入演算子で `return *this;` としたように、[[オブジェクト]]自身を返したい場合に使います。これにより、**メソッドチェーン**(`obj.setX(10).setY(20);` のような連続したメソッド呼び出し)が可能になります。 メソッドチェーンを実現する簡単な例を見てみましょう。 diff --git a/public/docs/cpp/7-classes-advanced/5-0-summary.md b/public/docs/cpp/7-classes-advanced/5-0-summary.md index 4476a8dc..20cb9e3a 100644 --- a/public/docs/cpp/7-classes-advanced/5-0-summary.md +++ b/public/docs/cpp/7-classes-advanced/5-0-summary.md @@ -7,11 +7,11 @@ question: [] ## この章のまとめ -この章では、クラスをより効果的に利用するための応用的な機能を学びました。 +この章では、[[クラス]]をより効果的に利用するための応用的な機能を学びました。 - * **オブジェクトのコピー**: [[ポインタ]]などリソースを管理するクラスでは、**コピーコンストラクタ**と**コピー代入演算子**を定義し、**深いコピー**を実装することが重要です。これにより、リソースの二重解放などの問題を未然に防ぎます。 + * **[[オブジェクト]]のコピー**: [[ポインタ]]などリソースを管理する[[クラス]]では、**コピーコンストラクタ**と**コピー代入演算子**を定義し、**深いコピー**を実装することが重要です。これにより、リソースの二重解放などの問題を未然に防ぎます。 * **演算子のオーバーロード**: `+` や `==` などの演算子を自作クラスに対して定義することで、コードの可読性を高め、直感的な操作を可能にします。 - * **staticメンバ**: `static`メンバ変数やメンバ関数は、クラスの全オブジェクトで共有されるデータや機能を提供します。オブジェクトを生成しなくてもアクセスできるのが特徴です。 - * **thisポインタ**: 非staticメンバ関数内で、呼び出し元のオブジェクト自身を指す[[ポインタ]]です。メンバ変数と引数の区別や、メソッドチェーンの実装に役立ちます。 + * **staticメンバ**: `static`メンバ変数やメンバ関数は、[[クラス]]の全[[オブジェクト]]で共有されるデータや機能を提供します。[[オブジェクト]]を生成しなくてもアクセスできるのが特徴です。 + * **thisポインタ**: 非static[[メンバ関数]]内で、呼び出し元の[[オブジェクト]]自身を指す[[ポインタ]]です。メンバ変数と引数の区別や、メソッドチェーンの実装に役立ちます。 -これらの機能を組み合わせることで、C++のクラスは単なるデータの入れ物から、振る舞いを伴った洗練された部品へと進化します。 +これらの機能を組み合わせることで、C++の[[クラス]]は単なるデータの入れ物から、振る舞いを伴った洗練された部品へと進化します。 diff --git a/public/docs/cpp/7-classes-advanced/5-1-practice1.md b/public/docs/cpp/7-classes-advanced/5-1-practice1.md index 22e445ce..497cfbac 100644 --- a/public/docs/cpp/7-classes-advanced/5-1-practice1.md +++ b/public/docs/cpp/7-classes-advanced/5-1-practice1.md @@ -9,9 +9,9 @@ question: ### 練習問題1: 複素数クラス -実部 (real) と虚部 (imaginary) を[[`double`]]型で持つ複素数クラス `Complex` を作成してください。以下の要件を満たすものとします。 +実部 (real) と虚部 (imaginary) を[[`double`]]型で持つ複素数[[クラス]] `Complex` を作成してください。以下の要件を満たすものとします。 -1. コンストラクタで実部と虚部を初期化できるようにする。 +1. [[コンストラクタ]]で実部と虚部を初期化できるようにする。 2. 複素数同士の足し算 (`+`) と掛け算 (`*`) を演算子オーバーロードで実装する。 * 加算: $(a+bi) + (c+di) = (a+c) + (b+d)i$ * 乗算: $(a+bi) \* (c+di) = (ac-bd) + (ad+bc)i$ diff --git a/public/docs/cpp/7-classes-advanced/5-2-practice2.md b/public/docs/cpp/7-classes-advanced/5-2-practice2.md index 76ce389e..ae848d0d 100644 --- a/public/docs/cpp/7-classes-advanced/5-2-practice2.md +++ b/public/docs/cpp/7-classes-advanced/5-2-practice2.md @@ -10,9 +10,9 @@ question: ### 練習問題2: 動的配列クラスのコピー制御 -整数 (`int`) の動的配列を管理するクラス `IntArray` を作成してください。このクラスは、コンストラクタで指定されたサイズの配列を [[`new`]] で確保し、デストラクタで `delete[]` を使って解放します。 +整数 (`int`) の動的配列を管理する[[クラス]] `IntArray` を作成してください。このクラスは、[[コンストラクタ]]で指定されたサイズの配列を [[`new`]] で確保し、デストラクタで `delete[]` を使って解放します。 -この `IntArray` クラスに対して、**深いコピー**を正しく行うための**コピーコンストラクタ**と**コピー代入演算子**を実装してください。 +この `IntArray` [[クラス]]に対して、**深いコピー**を正しく行うための**コピーコンストラクタ**と**コピー代入演算子**を実装してください。 ```cpp:practice8_2.cpp #include diff --git a/public/docs/cpp/8-inheritance/1-0-inheritance.md b/public/docs/cpp/8-inheritance/1-0-inheritance.md index 8f01a9a9..b4a89004 100644 --- a/public/docs/cpp/8-inheritance/1-0-inheritance.md +++ b/public/docs/cpp/8-inheritance/1-0-inheritance.md @@ -13,11 +13,11 @@ question: ## クラスの継承 -**継承**とは、既存のクラス(**親クラス**または**基底クラス**と呼びます)の機能を引き継いで、新しいクラス(**子クラス**または**派生クラス**と呼びます)を作成する仕組みです。これにより、共通の機能を何度も書く必要がなくなり、コードの重複を避けられます。 +**継承**とは、既存の[[クラス]](**親クラス**または**基底クラス**と呼びます)の機能を引き継いで、新しい[[クラス]](**子クラス**または**派生クラス**と呼びます)を作成する仕組みです。これにより、共通の機能を何度も書く必要がなくなり、コードの重複を避けられます。 -例えば、「動物」という大まかなクラスがあり、その特徴を引き継いで「犬」や「猫」といった具体的なクラスを作ることができます。「犬」も「猫」も「動物」が持つ「食べる」という共通の機能を持っていますよね。 +例えば、「動物」という大まかな[[クラス]]があり、その特徴を引き継いで「犬」や「猫」といった具体的な[[クラス]]を作ることができます。「犬」も「猫」も「動物」が持つ「食べる」という共通の機能を持っていますよね。 -C++では、クラス名の後に `: public 親クラス名` と書くことで継承を表現します。 +C++では、[[クラス]]名の後に `: public 親クラス名` と書くことで継承を表現します。 ```cpp:inheritance_basic.cpp #include @@ -61,4 +61,4 @@ Pochi is eating. Pochi says Woof! ``` -この例では、`Dog`クラスは`Animal`クラスを継承しています。そのため、`Dog`クラスのオブジェクト `my_dog` は、`Animal`クラスで定義されたメンバ変数 `name` やメンバ関数 `eat()` を、まるで自分のものであるかのように利用できます。 +この例では、`Dog`[[クラス]]は`Animal`[[クラス]]を継承しています。そのため、`Dog`[[クラス]]の[[オブジェクト]] `my_dog` は、`Animal`[[クラス]]で定義された[[メンバ変数]] `name` や[[メンバ関数]] `eat()` を、まるで自分のものであるかのように利用できます。 diff --git a/public/docs/cpp/8-inheritance/2-0-polymorphism.md b/public/docs/cpp/8-inheritance/2-0-polymorphism.md index 9290b4a8..6d55cc2d 100644 --- a/public/docs/cpp/8-inheritance/2-0-polymorphism.md +++ b/public/docs/cpp/8-inheritance/2-0-polymorphism.md @@ -15,7 +15,7 @@ question: これを実現するのが **仮想関数 (virtual function)** です。親クラスの関数宣言の前に `virtual` キーワードを付けると、その関数は仮想関数になります。 -親クラスの[[ポインタ]]や参照は、子クラスのオブジェクトを指すことができます。このとき、呼び出された仮想関数は、[[ポインタ]]が指している**オブジェクトの実際の型**に基づいて決定されます。 +親クラスの[[ポインタ]]や参照は、子クラスの[[オブジェクト]]を指すことができます。このとき、呼び出された仮想関数は、[[ポインタ]]が指している**[[オブジェクト]]の実際の型**に基づいて決定されます。 言葉だけでは難しいので、コードで見てみましょう。 @@ -73,4 +73,4 @@ Woof! Meow! ``` -`make_animal_speak` 関数は `Animal*` 型の引数を取りますが、`Dog`オブジェクトや`Cat`オブジェクトの[[アドレス]]を渡すことができています。そして、`animal->speak()` を呼び出すと、`animal` ポインタが実際に指しているオブジェクトの `speak()` が実行されます。これがポリモーフィズムです。もし `Animal`クラスの `speak()` に `virtual` が付いていなければ、どのオブジェクトを渡しても `Animal` の `speak()` が呼ばれてしまいます。 +`make_animal_speak` 関数は `Animal*` 型の引数を取りますが、`Dog`[[オブジェクト]]や`Cat`[[オブジェクト]]の[[アドレス]]を渡すことができています。そして、`animal->speak()` を呼び出すと、`animal` ポインタが実際に指している[[オブジェクト]]の `speak()` が実行されます。これがポリモーフィズムです。もし `Animal`[[クラス]]の `speak()` に `virtual` が付いていなければ、どの[[オブジェクト]]を渡しても `Animal` の `speak()` が呼ばれてしまいます。 diff --git a/public/docs/cpp/8-inheritance/4-0-abstract-class.md b/public/docs/cpp/8-inheritance/4-0-abstract-class.md index cf35b3f9..09683184 100644 --- a/public/docs/cpp/8-inheritance/4-0-abstract-class.md +++ b/public/docs/cpp/8-inheritance/4-0-abstract-class.md @@ -12,9 +12,9 @@ question: ## 抽象クラス -時には、「具体的な実装を持たず、子クラスに実装を強制するための設計図」としてのみ機能するクラスを定義したい場合があります。これが**抽象クラス (Abstract Class)** です。 +時には、「具体的な実装を持たず、子クラスに実装を強制するための設計図」としてのみ機能する[[クラス]]を定義したい場合があります。これが**抽象クラス (Abstract Class)** です。 -抽象クラスは、**純粋仮想関数 (pure virtual function)** を1つ以上持つクラスです。純粋仮想関数は、末尾に `= 0` を付けて宣言します。 +抽象クラスは、**純粋仮想関数 (pure virtual function)** を1つ以上持つ[[クラス]]です。純粋仮想関数は、末尾に `= 0` を付けて宣言します。 ```cpp virtual void function_name() = 0; // これが純粋仮想関数 @@ -22,7 +22,7 @@ virtual void function_name() = 0; // これが純粋仮想関数 抽象クラスは以下の特徴を持ちます。 - * インスタンス化(オブジェクトの作成)ができない。 + * [[インスタンス化]]([[オブジェクト]]の作成)ができない。 * 抽象クラスを継承した子クラスは、全ての純粋仮想関数をオーバーライド(実装)しなければならない。さもなければ、その子クラスもまた抽象クラスとなる。 ```cpp:abstract_class_example.cpp @@ -74,4 +74,4 @@ Drawing a circle: ○ Drawing a square: □ ``` -`Shape` クラスは「図形なら描画できるはずだ」というインターフェース(契約)を定義し、具体的な描画方法は子クラスである `Circle` や `Square` に任せています。このように、抽象クラスはプログラムの骨格となる設計を強制するのに非常に役立ちます。 +`Shape` [[クラス]]は「図形なら描画できるはずだ」というインターフェース(契約)を定義し、具体的な描画方法は子クラスである `Circle` や `Square` に任せています。このように、抽象クラスはプログラムの骨格となる設計を強制するのに非常に役立ちます。 diff --git a/public/docs/cpp/8-inheritance/5-0-summary.md b/public/docs/cpp/8-inheritance/5-0-summary.md index bf66a941..c72acd6d 100644 --- a/public/docs/cpp/8-inheritance/5-0-summary.md +++ b/public/docs/cpp/8-inheritance/5-0-summary.md @@ -7,8 +7,8 @@ question: [] ## この章のまとめ - * **継承**: 既存のクラスの機能を引き継ぎ、コードの再利用性を高める仕組みです。`(子クラス) : public (親クラス)` のように書きます。 + * **継承**: 既存の[[クラス]]の機能を引き継ぎ、コードの再利用性を高める仕組みです。`(子クラス) : public (親クラス)` のように書きます。 * **ポリモーフィズム**: 「同じ指示でも、オブジェクトの種類によって異なる振る舞いをさせる」性質です。 - * **仮想関数 (`virtual`)**: ポリモーフィズムを実現するための鍵です。親クラスの関数に `virtual` を付けると、[[ポインタ]]や参照経由で呼び出した際に、オブジェクトの実際の型に応じた関数が実行されます。 + * **仮想関数 (`virtual`)**: ポリモーフィズムを実現するための鍵です。親クラスの関数に `virtual` を付けると、[[ポインタ]]や参照経由で呼び出した際に、[[オブジェクト]]の実際の型に応じた関数が実行されます。 * **オーバーライド (`override`)**: 子クラスで親クラスの仮想関数を上書きする意図を明示します。コンパイラがチェックしてくれるため、安全性が向上します。 - * **抽象クラス**: 1つ以上の**純粋仮想関数 (`virtual ... = 0;`)** を持つクラスです。インスタンス化できず、継承されるための設計図として機能します。 + * **抽象クラス**: 1つ以上の**純粋仮想関数 (`virtual ... = 0;`)** を持つ[[クラス]]です。[[インスタンス化]]できず、継承されるための設計図として機能します。 diff --git a/public/docs/cpp/8-inheritance/5-1-practice1.md b/public/docs/cpp/8-inheritance/5-1-practice1.md index 4459a4d2..2af5aadb 100644 --- a/public/docs/cpp/8-inheritance/5-1-practice1.md +++ b/public/docs/cpp/8-inheritance/5-1-practice1.md @@ -9,9 +9,9 @@ question: ### 練習問題1:乗り物の階層構造 -`Vehicle` という親クラスを作成し、`move()` というメンバ関数を持たせましょう。次に、`Vehicle` を継承して `Car` クラスと `Motorcycle` クラスを作成し、それぞれが独自の `move()` の振る舞いをするようにオーバーライドしてください。 +`Vehicle` という親クラスを作成し、`move()` という[[メンバ関数]]を持たせましょう。次に、`Vehicle` を継承して `Car` [[クラス]]と `Motorcycle` [[クラス]]を作成し、それぞれが独自の `move()` の振る舞いをするようにオーバーライドしてください。 -[[`main` 関数]]では、`Vehicle` の[[ポインタ]]の配列を作成し、`Car` と `Motorcycle` のオブジェクトを格納して、ループでそれぞれの `move()` を呼び出してください。 +[[`main` 関数]]では、`Vehicle` の[[ポインタ]]の配列を作成し、`Car` と `Motorcycle` の[[オブジェクト]]を格納して、ループでそれぞれの `move()` を呼び出してください。 ```cpp:practice9_1.cpp #include diff --git a/public/docs/cpp/8-inheritance/5-2-practice2.md b/public/docs/cpp/8-inheritance/5-2-practice2.md index 995c02f0..b2f0a5bd 100644 --- a/public/docs/cpp/8-inheritance/5-2-practice2.md +++ b/public/docs/cpp/8-inheritance/5-2-practice2.md @@ -14,9 +14,9 @@ question: `Employee` という抽象クラスを定義してください。このクラスは、従業員の名前を保持し、給与を計算するための純粋仮想関数 `calculate_salary()` を持ちます。 -次に、`Employee` を継承して、`FullTimeEmployee`(月給制)と `PartTimeEmployee`(時給制)の2つのクラスを作成します。それぞれのクラスで `calculate_salary()` を具体的に実装してください。 +次に、`Employee` を継承して、`FullTimeEmployee`(月給制)と `PartTimeEmployee`(時給制)の2つの[[クラス]]を作成します。それぞれのクラスで `calculate_salary()` を具体的に実装してください。 -[[`main` 関数]]で、それぞれのクラスのインスタンスを作成し、給与が正しく計算されることを確認してください。 +[[`main` 関数]]で、それぞれのクラスの[[インスタンス]]を作成し、給与が正しく計算されることを確認してください。 ```cpp:practice9_2.cpp #include diff --git a/public/docs/cpp/9-templates/-intro.md b/public/docs/cpp/9-templates/-intro.md index b21c2904..681b24be 100644 --- a/public/docs/cpp/9-templates/-intro.md +++ b/public/docs/cpp/9-templates/-intro.md @@ -1,4 +1,4 @@ -これまでの章では、`int`や`double`、あるいは自作の`Car`クラスのように、特定の型に対して処理を行う関数やクラスを作成してきました。しかし、プログラムが複雑になるにつれて、「型は違うけれど、行いたい処理は全く同じ」という状況が頻繁に発生します。例えば、2つの値の大きい方を返す`max`という関数を考えてみましょう。 +これまでの章では、[[`int`]]や[[`double`]]、あるいは自作の`Car`[[クラス]]のように、特定の型に対して処理を行う関数やクラスを作成してきました。しかし、プログラムが複雑になるにつれて、「型は違うけれど、行いたい処理は全く同じ」という状況が頻繁に発生します。例えば、2つの値の大きい方を返す`max`という関数を考えてみましょう。 ```cpp int max_int(int a, int b) { diff --git a/public/docs/cpp/9-templates/2-0-class-template.md b/public/docs/cpp/9-templates/2-0-class-template.md index 2750bcbe..369b771e 100644 --- a/public/docs/cpp/9-templates/2-0-class-template.md +++ b/public/docs/cpp/9-templates/2-0-class-template.md @@ -12,7 +12,7 @@ question: ## クラステンプレート: 様々な型のデータを格納できるクラスを作る -テンプレートの力は、クラスにも適用できます。これにより、様々な型のデータを格納できる汎用的なクラス(コンテナなど)を作成できます。例えば、「2つの値をペアで保持する」クラスを考えてみましょう。 +テンプレートの力は、[[クラス]]にも適用できます。これにより、様々な型のデータを格納できる汎用的な[[クラス]](コンテナなど)を作成できます。例えば、「2つの値をペアで保持する」[[クラス]]を考えてみましょう。 ```cpp:class_template_intro.cpp #include diff --git a/public/docs/cpp/9-templates/2-1-class-template-detail.md b/public/docs/cpp/9-templates/2-1-class-template-detail.md index 2590ee35..6f7d8a22 100644 --- a/public/docs/cpp/9-templates/2-1-class-template-detail.md +++ b/public/docs/cpp/9-templates/2-1-class-template-detail.md @@ -15,10 +15,10 @@ question: 関数テンプレートと基本的な考え方は同じですが、いくつか重要な違いがあります。 1. **明示的な型指定**: - 関数テンプレートではコンパイラが型を推論してくれましたが、クラステンプレートの場合は、オブジェクトを生成する際に`Pair`のように、開発者が明示的に型を指定する必要があります。 + 関数テンプレートではコンパイラが型を推論してくれましたが、クラステンプレートの場合は、[[オブジェクト]]を生成する際に`Pair`のように、開発者が明示的に型を指定する必要があります。 2. **インスタンス化**: - `Pair`のように具体的な型を指定してオブジェクトを作ることを、テンプレートの**インスタンス化**と呼びます。コンパイラは、この指定に基づいて`T1`を`int`に、`T2`を`std::string`に置き換えた、以下のような新しいクラスを内部的に生成します。 + `Pair`のように具体的な型を指定して[[オブジェクト]]を作ることを、テンプレートの**インスタンス化**と呼びます。コンパイラは、この指定に基づいて`T1`を`int`に、`T2`を`std::string`に置き換えた、以下のような新しい[[クラス]]を内部的に生成します。 ```cpp // コンパイラが内部的に生成するクラスのイメージ @@ -35,6 +35,6 @@ question: }; ``` - `Pair`と`Pair`は、[[コンパイル]]されると全く別のクラスとして扱われることに注意してください。 + `Pair`と`Pair`は、[[コンパイル]]されると全く別の[[クラス]]として扱われることに注意してください。 クラステンプレートは、C++の強力なライブラリである**STL (Standard Template Library)**の根幹をなす技術です。[[./next]]で学ぶ`vector`や`map`といった便利なコンテナは、すべてクラステンプレートで実装されています。 diff --git a/public/docs/cpp/9-templates/3-0-summary.md b/public/docs/cpp/9-templates/3-0-summary.md index ba8c9203..d46532e6 100644 --- a/public/docs/cpp/9-templates/3-0-summary.md +++ b/public/docs/cpp/9-templates/3-0-summary.md @@ -10,6 +10,6 @@ question: [] * **ジェネリックプログラミング**は、特定の型に縛られない、汎用的なコードを書くための手法です。 * **テンプレート**は、C++でジェネリックプログラミングを実現するための機能です。 * **関数テンプレート**を使うと、様々な型の引数に対して同じ処理を行う関数を定義できます。呼び出し時には、コンパイラが**テンプレート引数推論**によって型を自動的に決定します。 - * **クラステンプレート**を使うと、様々な型を扱える汎用的なクラスを定義できます。オブジェクトを生成する際には、`< >`内に具体的な型を**明示的に指定**してインスタンス化する必要があります。 + * **クラステンプレート**を使うと、様々な型を扱える汎用的な[[クラス]]を定義できます。[[オブジェクト]]を生成する際には、`< >`内に具体的な型を**明示的に指定**してインスタンス化する必要があります。 テンプレートを使いこなすことで、コードの再利用性が劇的に向上し、より柔軟で堅牢なプログラムを記述できるようになります。 diff --git a/public/docs/cpp/9-templates/3-2-practice2.md b/public/docs/cpp/9-templates/3-2-practice2.md index bc524992..f2c2d5ba 100644 --- a/public/docs/cpp/9-templates/3-2-practice2.md +++ b/public/docs/cpp/9-templates/3-2-practice2.md @@ -12,7 +12,7 @@ question: ### 練習問題2: 汎用的なスタッククラス -後入れ先出し(LIFO)のデータ構造であるスタックを、クラステンプレート`SimpleStack`として実装してください。以下のメンバ関数を持つようにしてください。 +後入れ先出し(LIFO)のデータ構造であるスタックを、クラステンプレート`SimpleStack`として実装してください。以下の[[メンバ関数]]を持つようにしてください。 * `void push(T item)`: スタックに要素を追加する * `T pop()`: スタックの先頭から要素を取り出す From 62d34973ad39dab93cd0ec44702a02b2d4af45ce Mon Sep 17 00:00:00 2001 From: na-trium-144 <100704180+na-trium-144@users.noreply.github.com> Date: Wed, 12 Aug 2026 00:19:45 +0900 Subject: [PATCH 8/9] c++ 7 --- .../cpp/7-classes-advanced/1-2-deep-copy.md | 20 +++++++++++-------- .../2-0-operator-overload.md | 2 +- .../7-classes-advanced/3-0-static-member.md | 5 ++++- .../docs/cpp/7-classes-advanced/4-0-this.md | 7 ++++++- .../cpp/7-classes-advanced/5-0-summary.md | 6 +++--- .../cpp/7-classes-advanced/5-1-practice1.md | 2 +- .../cpp/7-classes-advanced/5-2-practice2.md | 2 +- 7 files changed, 28 insertions(+), 16 deletions(-) diff --git a/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md b/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md index 04f014fa..4b97bd8f 100644 --- a/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md +++ b/public/docs/cpp/7-classes-advanced/1-2-deep-copy.md @@ -10,12 +10,22 @@ question: の「const」と「&」はそれぞれ何の意味ですか? - コピー代入演算子で自己代入のチェック (if (this == &other)) が必要なのはなぜですか? - デストラクタでif (m_data != nullptr)というチェックがありますが、これはなぜ必要なのですか? +term: + - コピーコンストラクタ + - コピー代入演算子 --- ### 解決策:コピー機能を自作する (深いコピー) この問題を解決するために、**コピーコンストラクタ**と**コピー代入演算子**を自分で定義して、「深いコピー」を実装します。深いコピーとは、[[ポインタ]]の指す先の実体(データそのもの)を新しく作ってコピーすることです。 +| 機能 | いつ呼ばれるか | 何をするか | +| :--- | :--- | :--- | +| **コピーコンストラクタ** | [[オブジェクト]]が**作られる時**に、他の[[オブジェクト]]で[[初期化]]される場合
`ResourceHolder r2 = r1;` | 新しいリソースを確保し、元の[[オブジェクト]]の**値**をコピーする。 | +| **コピー代入演算子** | **既にある[[オブジェクト]]**に、他の[[オブジェクト]]を代入する場合
`r3 = r1;` | 1. 自分が持っている古いリソースを解放する。
2. 新しいリソースを確保し、元の[[オブジェクト]]の**値**をコピーする。 | + +[[ポインタ]]でリソースを管理する[[クラス]]では、安全なコピーを実現するためにこの2つの関数を自分で定義することが不可欠です。 + ```cpp:resource_holder.cpp #include @@ -120,13 +130,7 @@ Resource 10 destroyed. (at 0x139f06600) Resource 10 destroyed. (at 0x139f065e0) ``` -*(メモリアドレスは実行するたびに変わります)* +> [!NOTE] +> (メモリアドレスは実行するたびに変わります) 実行結果を見ると、`rh1`, `rh2`, `rh3` はそれぞれ異なるメモリ[[アドレス]] (`Address`) を持っていることがわかります。これにより、各[[オブジェクト]]は独立したリソースを管理でき、プログラム終了時にそれぞれの[[デストラクタ]]が安全にメモリを解放できます。 - -| 機能 | いつ呼ばれるか | 何をするか | -| :--- | :--- | :--- | -| **コピーコンストラクタ** | [[オブジェクト]]が**作られる時**に、他の[[オブジェクト]]で[[初期化]]される場合
`ResourceHolder r2 = r1;` | 新しいリソースを確保し、元の[[オブジェクト]]の**値**をコピーする。 | -| **コピー代入演算子** | **既にある[[オブジェクト]]**に、他の[[オブジェクト]]を代入する場合
`r3 = r1;` | 1. 自分が持っている古いリソースを解放する。
2. 新しいリソースを確保し、元の[[オブジェクト]]の**値**をコピーする。 | - -このように、[[ポインタ]]でリソースを管理する[[クラス]]では、安全なコピーを実現するためにこの2つの関数を自分で定義することが不可欠です。 diff --git a/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md b/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md index 8ca61f3d..239c801f 100644 --- a/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md +++ b/public/docs/cpp/7-classes-advanced/2-0-operator-overload.md @@ -25,7 +25,7 @@ C++では、`+`, `-`, `==`, `<<` などの組み込み演算子を、自作の[[ | 単項演算子 (`-`, `!` etc.) | `T operator-();` | `T operator-(const T& obj);` | > [!WARNING] -> `operator<<` は、左辺のオペランドが `std::ostream` 型(`std::cout` など)であるため、`Vector2D` の[[メンバ関数]]としては定義できません。そのため、非メンバ関数として定義するのが一般的です。 +> `operator<<` は、左辺のオペランドが `std::ostream` 型([[`std::cout`]] など)であるため、`Vector2D` の[[メンバ関数]]としては定義できません。そのため、非メンバ関数として定義するのが一般的です。 `Vector2D` [[クラス]]で `+`(加算)、`==`(等価比較)、`<<`(ストリーム出力)をオーバーロードしてみましょう。 diff --git a/public/docs/cpp/7-classes-advanced/3-0-static-member.md b/public/docs/cpp/7-classes-advanced/3-0-static-member.md index 3bdee0f8..fa80bf43 100644 --- a/public/docs/cpp/7-classes-advanced/3-0-static-member.md +++ b/public/docs/cpp/7-classes-advanced/3-0-static-member.md @@ -7,6 +7,9 @@ question: - staticメンバ変数の定義をクラス定義の外で行うのはなぜですか?クラス定義の中に書けないのですか? - staticメンバ関数から、nameなどの非staticメンバにアクセスできないのはなぜですか? - Player::getPlayerCount()のように、オブジェクトがなくてもstaticメンバ関数を呼び出せるのはどのような場合に便利ですか? +term: + - staticメンバ + - クラス変数 --- ## staticメンバ @@ -18,7 +21,7 @@ question: * **宣言**: クラス定義の中で `static` を付けて行います。 * **定義**: クラス定義の外([[ソースファイル]])で、メモリ上の実体を確保し、初期化します。 -`static` キーワードを付けて宣言された[[メンバ関数]]は、特定の[[オブジェクト]]に依存せずに呼び出せます。そのため、`this` ポインタ(後述)を持ちません。 +`static` キーワードを付けて宣言された[[メンバ関数]]は、特定の[[オブジェクト]]に依存せずに呼び出せます。そのため、[[`this` ポインタ]]を持ちません。 * **アクセス**: staticメンバ変数や他のstaticメンバ関数にはアクセスできますが、非staticなメンバ([[インスタンス]]ごとのメンバ変数やメンバ関数)にはアクセスできません。 * **呼び出し**: `クラス名::関数名()` のように、[[オブジェクト]]を生成しなくても呼び出せます。 diff --git a/public/docs/cpp/7-classes-advanced/4-0-this.md b/public/docs/cpp/7-classes-advanced/4-0-this.md index 88e9da05..9c04efd6 100644 --- a/public/docs/cpp/7-classes-advanced/4-0-this.md +++ b/public/docs/cpp/7-classes-advanced/4-0-this.md @@ -6,6 +6,11 @@ question: - thisポインタは、なぜメンバ関数に「暗黙的に渡される」のですか?明示的に渡すことはできないのですか? - this->x = newX; のように this-> を付けなくても x = newX; と書けば良い場面はありますか? - メソッドチェーンは、オブジェクトを何度もコピーしているわけではないのですか? +term: + - this + - thisポインタ + - this ポインタ + - メソッドチェーン --- ## thisポインタ @@ -26,7 +31,7 @@ question: ``` 2. **自分自身の参照や[[ポインタ]]を返す場合** - コピー代入演算子で `return *this;` としたように、[[オブジェクト]]自身を返したい場合に使います。これにより、**メソッドチェーン**(`obj.setX(10).setY(20);` のような連続したメソッド呼び出し)が可能になります。 + [[コピー代入演算子]]で `return *this;` としたように、[[オブジェクト]]自身を返したい場合に使います。これにより、**メソッドチェーン**(`obj.setX(10).setY(20);` のような連続したメソッド呼び出し)が可能になります。 メソッドチェーンを実現する簡単な例を見てみましょう。 diff --git a/public/docs/cpp/7-classes-advanced/5-0-summary.md b/public/docs/cpp/7-classes-advanced/5-0-summary.md index 20cb9e3a..c2e8d5d6 100644 --- a/public/docs/cpp/7-classes-advanced/5-0-summary.md +++ b/public/docs/cpp/7-classes-advanced/5-0-summary.md @@ -9,9 +9,9 @@ question: [] この章では、[[クラス]]をより効果的に利用するための応用的な機能を学びました。 - * **[[オブジェクト]]のコピー**: [[ポインタ]]などリソースを管理する[[クラス]]では、**コピーコンストラクタ**と**コピー代入演算子**を定義し、**深いコピー**を実装することが重要です。これにより、リソースの二重解放などの問題を未然に防ぎます。 + * **[[オブジェクト]]のコピー**: [[ポインタ]]などリソースを管理する[[クラス]]では、**[[コピーコンストラクタ]]**と**[[コピー代入演算子]]**を定義し、**深いコピー**を実装することが重要です。これにより、リソースの二重解放などの問題を未然に防ぎます。 * **演算子のオーバーロード**: `+` や `==` などの演算子を自作クラスに対して定義することで、コードの可読性を高め、直感的な操作を可能にします。 - * **staticメンバ**: `static`メンバ変数やメンバ関数は、[[クラス]]の全[[オブジェクト]]で共有されるデータや機能を提供します。[[オブジェクト]]を生成しなくてもアクセスできるのが特徴です。 - * **thisポインタ**: 非static[[メンバ関数]]内で、呼び出し元の[[オブジェクト]]自身を指す[[ポインタ]]です。メンバ変数と引数の区別や、メソッドチェーンの実装に役立ちます。 + * **[[staticメンバ]]**: `static`メンバ変数やメンバ関数は、[[クラス]]の全[[オブジェクト]]で共有されるデータや機能を提供します。[[オブジェクト]]を生成しなくてもアクセスできるのが特徴です。 + * **[[thisポインタ]]**: 非static[[メンバ関数]]内で、呼び出し元の[[オブジェクト]]自身を指す[[ポインタ]]です。メンバ変数と引数の区別や、[[メソッドチェーン]]の実装に役立ちます。 これらの機能を組み合わせることで、C++の[[クラス]]は単なるデータの入れ物から、振る舞いを伴った洗練された部品へと進化します。 diff --git a/public/docs/cpp/7-classes-advanced/5-1-practice1.md b/public/docs/cpp/7-classes-advanced/5-1-practice1.md index 497cfbac..7f51d9dc 100644 --- a/public/docs/cpp/7-classes-advanced/5-1-practice1.md +++ b/public/docs/cpp/7-classes-advanced/5-1-practice1.md @@ -15,7 +15,7 @@ question: 2. 複素数同士の足し算 (`+`) と掛け算 (`*`) を演算子オーバーロードで実装する。 * 加算: $(a+bi) + (c+di) = (a+c) + (b+d)i$ * 乗算: $(a+bi) \* (c+di) = (ac-bd) + (ad+bc)i$ -3. `std::cout` で `(a + bi)` という形式で出力できるように、`<<` 演算子をオーバーロードする。(虚部が負の場合は `(a - bi)` のように表示されるとより良い) +3. [[`std::cout`]] で `(a + bi)` という形式で出力できるように、`<<` 演算子をオーバーロードする。(虚部が負の場合は `(a - bi)` のように表示されるとより良い) ```cpp:practice8_1.cpp #include diff --git a/public/docs/cpp/7-classes-advanced/5-2-practice2.md b/public/docs/cpp/7-classes-advanced/5-2-practice2.md index ae848d0d..0f7bff86 100644 --- a/public/docs/cpp/7-classes-advanced/5-2-practice2.md +++ b/public/docs/cpp/7-classes-advanced/5-2-practice2.md @@ -12,7 +12,7 @@ question: 整数 (`int`) の動的配列を管理する[[クラス]] `IntArray` を作成してください。このクラスは、[[コンストラクタ]]で指定されたサイズの配列を [[`new`]] で確保し、デストラクタで `delete[]` を使って解放します。 -この `IntArray` [[クラス]]に対して、**深いコピー**を正しく行うための**コピーコンストラクタ**と**コピー代入演算子**を実装してください。 +この `IntArray` [[クラス]]に対して、**深いコピー**を正しく行うための**[[コピーコンストラクタ]]**と**[[コピー代入演算子]]**を実装してください。 ```cpp:practice8_2.cpp #include From 86a949a26814cd99ea8607e334cf12cce78b7853 Mon Sep 17 00:00:00 2001 From: na-trium-144 <100704180+na-trium-144@users.noreply.github.com> Date: Sat, 15 Aug 2026 23:35:49 +0900 Subject: [PATCH 9/9] c++ 8 --- public/docs/cpp/8-inheritance/1-0-inheritance.md | 10 ++++++++-- public/docs/cpp/8-inheritance/2-0-polymorphism.md | 11 ++++++++--- public/docs/cpp/8-inheritance/3-0-override.md | 9 ++++++--- public/docs/cpp/8-inheritance/4-0-abstract-class.md | 9 ++++++--- public/docs/cpp/8-inheritance/5-0-summary.md | 10 +++++----- public/docs/cpp/8-inheritance/5-1-practice1.md | 2 +- public/docs/cpp/8-inheritance/5-2-practice2.md | 2 +- 7 files changed, 35 insertions(+), 18 deletions(-) diff --git a/public/docs/cpp/8-inheritance/1-0-inheritance.md b/public/docs/cpp/8-inheritance/1-0-inheritance.md index b4a89004..580ba851 100644 --- a/public/docs/cpp/8-inheritance/1-0-inheritance.md +++ b/public/docs/cpp/8-inheritance/1-0-inheritance.md @@ -9,6 +9,12 @@ question: にするとどうなりますか? - 親クラスのメンバ変数 `name` は、子クラスで自動的に使えるようになるのですか? - '`Dog` クラスが `Animal` と `Canine` のように、複数のクラスから同時に継承することはできますか?' +term: + - 継承 + - 親クラス + - 基底クラス + - 子クラス + - 派生クラス --- ## クラスの継承 @@ -19,6 +25,8 @@ question: C++では、[[クラス]]名の後に `: public 親クラス名` と書くことで継承を表現します。 +以下の例では、`Dog`[[クラス]]は`Animal`[[クラス]]を継承しています。そのため、`Dog`[[クラス]]の[[オブジェクト]] `my_dog` は、`Animal`[[クラス]]で定義された[[メンバ変数]] `name` や[[メンバ関数]] `eat()` を、まるで自分のものであるかのように利用できます。 + ```cpp:inheritance_basic.cpp #include #include @@ -60,5 +68,3 @@ int main() { Pochi is eating. Pochi says Woof! ``` - -この例では、`Dog`[[クラス]]は`Animal`[[クラス]]を継承しています。そのため、`Dog`[[クラス]]の[[オブジェクト]] `my_dog` は、`Animal`[[クラス]]で定義された[[メンバ変数]] `name` や[[メンバ関数]] `eat()` を、まるで自分のものであるかのように利用できます。 diff --git a/public/docs/cpp/8-inheritance/2-0-polymorphism.md b/public/docs/cpp/8-inheritance/2-0-polymorphism.md index 6d55cc2d..303db4df 100644 --- a/public/docs/cpp/8-inheritance/2-0-polymorphism.md +++ b/public/docs/cpp/8-inheritance/2-0-polymorphism.md @@ -7,15 +7,20 @@ question: - '`virtual` キーワードを付けないとどうなりますか?例の `make_animal_speak` 関数ではどういう結果になりますか?' - なぜ `Animal*` のポインタや参照を使う必要があるのですか?直接オブジェクトを渡すのと何が違いますか? - 親クラスのポインタが子クラスのオブジェクトを指せるのはなぜですか? +term: + - 仮想関数 + - ポリモーフィズム + - 多態性 + - virtual --- ## 仮想関数 (virtual) とポリモーフィズム -継承の最も強力な側面は、**ポリモーフィズム(多態性)**を実現できることです。ポリモーフィズムとは、ギリシャ語で「多くの形を持つ」という意味で、プログラミングにおいては「**同じインターフェース(指示)で、オブジェクトの種類に応じて異なる振る舞いをさせる**」ことを指します。 +[[継承]]の最も強力な側面は、**ポリモーフィズム(多態性)**を実現できることです。ポリモーフィズムとは、ギリシャ語で「多くの形を持つ」という意味で、プログラミングにおいては「**同じインターフェース(指示)で、オブジェクトの種類に応じて異なる振る舞いをさせる**」ことを指します。 -これを実現するのが **仮想関数 (virtual function)** です。親クラスの関数宣言の前に `virtual` キーワードを付けると、その関数は仮想関数になります。 +これを実現するのが **仮想関数 (virtual function)** です。[[親クラス]]の関数宣言の前に `virtual` キーワードを付けると、その関数は仮想関数になります。 -親クラスの[[ポインタ]]や参照は、子クラスの[[オブジェクト]]を指すことができます。このとき、呼び出された仮想関数は、[[ポインタ]]が指している**[[オブジェクト]]の実際の型**に基づいて決定されます。 +[[親クラス]]の[[ポインタ]]や参照は、[[子クラス]]の[[オブジェクト]]を指すことができます。このとき、呼び出された仮想関数は、[[ポインタ]]が指している**[[オブジェクト]]の実際の型**に基づいて決定されます。 言葉だけでは難しいので、コードで見てみましょう。 diff --git a/public/docs/cpp/8-inheritance/3-0-override.md b/public/docs/cpp/8-inheritance/3-0-override.md index 9b811cb8..53ad820f 100644 --- a/public/docs/cpp/8-inheritance/3-0-override.md +++ b/public/docs/cpp/8-inheritance/3-0-override.md @@ -6,13 +6,16 @@ question: - '`override` を付けなくても、子クラスで親クラスと同じ名前の関数を定義すれば、それが呼ばれるのではないのですか?' - '`override` を付けることで具体的にどのようなバグが防げるのですか?' - '`final` というキーワードも見たことがあります。`override` と `final` はどう違うのですか?' +term: + - オーバーライド + - override --- ## オーバーライド (override) -先ほどの例で `override` というキーワードが登場しましたね。これはC++11から導入されたもので、子クラスの関数が**親クラスの仮想関数を上書き(オーバーライド)する意図があることを明示する**ためのものです。 +先ほどの例で `override` というキーワードが登場しましたね。これはC++11から導入されたもので、[[子クラス]]の関数が**[[親クラス]]の[[仮想関数]]を上書き(オーバーライド)する意図があることを明示する**ためのものです。 -`override` を付けておくと、もし親クラスに対応する仮想関数が存在しない場合(例えば、関数名をタイプミスした場合など)に、コンパイラがエラーを検出してくれます。 +`override` を付けておくと、もし[[親クラス]]に対応する[[仮想関数]]が存在しない場合(例えば、関数名をタイプミスした場合など)に、コンパイラがエラーを検出してくれます。 ```cpp class Dog : public Animal { @@ -25,4 +28,4 @@ public: }; ``` -意図しないバグを防ぐために、仮想関数をオーバーライドする際は必ず `override` を付ける習慣をつけましょう。 +意図しないバグを防ぐために、[[仮想関数]]をオーバーライドする際は必ず `override` を付ける習慣をつけましょう。 diff --git a/public/docs/cpp/8-inheritance/4-0-abstract-class.md b/public/docs/cpp/8-inheritance/4-0-abstract-class.md index 09683184..f1b674c1 100644 --- a/public/docs/cpp/8-inheritance/4-0-abstract-class.md +++ b/public/docs/cpp/8-inheritance/4-0-abstract-class.md @@ -8,11 +8,14 @@ question: - 抽象クラスを使うと、どんな良いことがありますか? - '`virtual ~Shape() {}` のように、デストラクタに `virtual` を付けるのはなぜですか?' - もし子クラスが純粋仮想関数を実装しなかったらどうなりますか? +term: + - 抽象クラス + - 純粋仮想関数 --- ## 抽象クラス -時には、「具体的な実装を持たず、子クラスに実装を強制するための設計図」としてのみ機能する[[クラス]]を定義したい場合があります。これが**抽象クラス (Abstract Class)** です。 +時には、「具体的な実装を持たず、[[子クラス]]に実装を強制するための設計図」としてのみ機能する[[クラス]]を定義したい場合があります。これが**抽象クラス (Abstract Class)** です。 抽象クラスは、**純粋仮想関数 (pure virtual function)** を1つ以上持つ[[クラス]]です。純粋仮想関数は、末尾に `= 0` を付けて宣言します。 @@ -23,7 +26,7 @@ virtual void function_name() = 0; // これが純粋仮想関数 抽象クラスは以下の特徴を持ちます。 * [[インスタンス化]]([[オブジェクト]]の作成)ができない。 - * 抽象クラスを継承した子クラスは、全ての純粋仮想関数をオーバーライド(実装)しなければならない。さもなければ、その子クラスもまた抽象クラスとなる。 + * 抽象クラスを[[継承]]した[[子クラス]]は、全ての純粋仮想関数を[[オーバーライド]](実装)しなければならない。さもなければ、その[[子クラス]]もまた抽象クラスとなる。 ```cpp:abstract_class_example.cpp #include @@ -74,4 +77,4 @@ Drawing a circle: ○ Drawing a square: □ ``` -`Shape` [[クラス]]は「図形なら描画できるはずだ」というインターフェース(契約)を定義し、具体的な描画方法は子クラスである `Circle` や `Square` に任せています。このように、抽象クラスはプログラムの骨格となる設計を強制するのに非常に役立ちます。 +`Shape` [[クラス]]は「図形なら描画できるはずだ」というインターフェース(契約)を定義し、具体的な描画方法は[[子クラス]]である `Circle` や `Square` に任せています。このように、抽象クラスはプログラムの骨格となる設計を強制するのに非常に役立ちます。 diff --git a/public/docs/cpp/8-inheritance/5-0-summary.md b/public/docs/cpp/8-inheritance/5-0-summary.md index c72acd6d..ce7452e3 100644 --- a/public/docs/cpp/8-inheritance/5-0-summary.md +++ b/public/docs/cpp/8-inheritance/5-0-summary.md @@ -7,8 +7,8 @@ question: [] ## この章のまとめ - * **継承**: 既存の[[クラス]]の機能を引き継ぎ、コードの再利用性を高める仕組みです。`(子クラス) : public (親クラス)` のように書きます。 - * **ポリモーフィズム**: 「同じ指示でも、オブジェクトの種類によって異なる振る舞いをさせる」性質です。 - * **仮想関数 (`virtual`)**: ポリモーフィズムを実現するための鍵です。親クラスの関数に `virtual` を付けると、[[ポインタ]]や参照経由で呼び出した際に、[[オブジェクト]]の実際の型に応じた関数が実行されます。 - * **オーバーライド (`override`)**: 子クラスで親クラスの仮想関数を上書きする意図を明示します。コンパイラがチェックしてくれるため、安全性が向上します。 - * **抽象クラス**: 1つ以上の**純粋仮想関数 (`virtual ... = 0;`)** を持つ[[クラス]]です。[[インスタンス化]]できず、継承されるための設計図として機能します。 + * **[[継承]]**: 既存の[[クラス]]の機能を引き継ぎ、コードの再利用性を高める仕組みです。`(子クラス) : public (親クラス)` のように書きます。 + * **[[ポリモーフィズム]]**: 「同じ指示でも、オブジェクトの種類によって異なる振る舞いをさせる」性質です。 + * **[[仮想関数]] (`virtual`)**: ポリモーフィズムを実現するための鍵です。[[親クラス]]の関数に `virtual` を付けると、[[ポインタ]]や参照経由で呼び出した際に、[[オブジェクト]]の実際の型に応じた関数が実行されます。 + * **[[オーバーライド]] (`override`)**: [[子クラス]]で[[親クラス]]の[[仮想関数]]を上書きする意図を明示します。コンパイラがチェックしてくれるため、安全性が向上します。 + * **[[抽象クラス]]**: 1つ以上の**[[純粋仮想関数]] (`virtual ... = 0;`)** を持つ[[クラス]]です。[[インスタンス化]]できず、[[継承]]されるための設計図として機能します。 diff --git a/public/docs/cpp/8-inheritance/5-1-practice1.md b/public/docs/cpp/8-inheritance/5-1-practice1.md index 2af5aadb..3bd813be 100644 --- a/public/docs/cpp/8-inheritance/5-1-practice1.md +++ b/public/docs/cpp/8-inheritance/5-1-practice1.md @@ -9,7 +9,7 @@ question: ### 練習問題1:乗り物の階層構造 -`Vehicle` という親クラスを作成し、`move()` という[[メンバ関数]]を持たせましょう。次に、`Vehicle` を継承して `Car` [[クラス]]と `Motorcycle` [[クラス]]を作成し、それぞれが独自の `move()` の振る舞いをするようにオーバーライドしてください。 +`Vehicle` という親クラスを作成し、`move()` という[[メンバ関数]]を持たせましょう。次に、`Vehicle` を継承して `Car` [[クラス]]と `Motorcycle` [[クラス]]を作成し、それぞれが独自の `move()` の振る舞いをするように[[オーバーライド]]してください。 [[`main` 関数]]では、`Vehicle` の[[ポインタ]]の配列を作成し、`Car` と `Motorcycle` の[[オブジェクト]]を格納して、ループでそれぞれの `move()` を呼び出してください。 diff --git a/public/docs/cpp/8-inheritance/5-2-practice2.md b/public/docs/cpp/8-inheritance/5-2-practice2.md index b2f0a5bd..4c6a9db7 100644 --- a/public/docs/cpp/8-inheritance/5-2-practice2.md +++ b/public/docs/cpp/8-inheritance/5-2-practice2.md @@ -12,7 +12,7 @@ question: ### 問題2: 従業員の給与計算 -`Employee` という抽象クラスを定義してください。このクラスは、従業員の名前を保持し、給与を計算するための純粋仮想関数 `calculate_salary()` を持ちます。 +`Employee` という[[抽象クラス]]を定義してください。このクラスは、従業員の名前を保持し、給与を計算するための[[純粋仮想関数]] `calculate_salary()` を持ちます。 次に、`Employee` を継承して、`FullTimeEmployee`(月給制)と `PartTimeEmployee`(時給制)の2つの[[クラス]]を作成します。それぞれのクラスで `calculate_salary()` を具体的に実装してください。