C++

C++入門

コンパイルと実行を繰り返し、メモリの安全性も意識しながら基礎を学びましょう。

この講座はC++17以降を対象にしています。

01

C++をコンパイルしてみよう

C++はゲーム、組み込み、リアルタイム処理など、性能が重要な分野で使われます。GCCまたはClangなどのコンパイラを導入します。

main.cppC++
#include <iostream>

int main() {
    std::cout << "こんにちは、C++!\n";
    return 0;
}
コンパイルと実行COMMAND
g++ -std=c++17 -Wall -Wextra main.cpp -o app
./app
実行結果OUTPUT
こんにちは、C++!
Windows PowerShellでは実行ファイル名をapp.exeにし、.\app.exeで実行します。警告オプションは常に有効にしましょう。
02

変数とデータ型

C++は変数の型を明示します。変更しない値はconstを付け、波括弧で初期化すると意図しない縮小変換を防げます。

主な型C++
std::string name{"Mity"};
int age{20};
double height{170.5};
bool is_student{true};
const int birth_month{8};

std::cout << name << "さん " << age << "歳\n";
std::cout << std::boolalpha << is_student << " " << birth_month << "月\n";
実行結果OUTPUT
Mityさん 20歳
true 8月

std::stringを使うには#include <string>が必要です。変数を初期化せず読むと未定義動作になるため、宣言時に値を入れます。

03

入力と検証

std::cinは型に応じて入力を読みます。読み込み失敗をifで確認します。

年齢を受け取るC++
int age{};
std::cout << "年齢: ";

if (std::cin >> age) {
    std::cout << "来年は" << age + 1 << "歳です\n";
} else {
    std::cout << "整数で入力してください\n";
}
実行例OUTPUT
年齢: 20
来年は21歳です

空白を含む一行はstd::getline(std::cin, text)で読みます。>>の後に併用するときは残った改行に注意が必要です。

04

演算子と条件分岐

整数同士の/は小数部分を切り捨てます。小数の結果が必要ならどちらかをdoubleにします。

点数を判定C++
int score{82};
if (score >= 80) {
    std::cout << "合格(よくできました)\n";
} else if (score >= 60) {
    std::cout << "合格\n";
} else {
    std::cout << "再挑戦\n";
}
実行結果OUTPUT
合格(よくできました)
05

繰り返し

forは初期化、条件、更新を指定します。whileは条件が真の間繰り返します。

1から5までC++
for (int i{1}; i <= 5; ++i) {
    std::cout << i << "回目\n";
}
実行結果OUTPUT
1回目
2回目
3回目
4回目
5回目
範囲外アクセス 配列やvectorの使える位置を超えないようにします。要素数はsize()で確認できます。
06

vectorとmap

std::vectorは可変長の配列、std::mapはキーと値の組です。

値を追加して読むC++
std::vector<std::string> fruits{"りんご", "みかん"};
fruits.push_back("ぶどう");
std::map<std::string, int> scores{{"Aki", 82}, {"Mika", 91}};

for (const auto& fruit : fruits) {
    std::cout << fruit << '\n';
}
std::cout << "Mika: " << scores.at("Mika") << "点\n";
実行結果OUTPUT
りんご
みかん
ぶどう
Mika: 91点

at()はキーがないと例外を出します。存在確認にはfind()やC++20のcontains()を使います。

07

関数と参照

intのような小さな型は値渡しが適しています。一方、std::stringのような大きくなり得る値をコピーせず受け取るときはconst T&を使い、関数内で変更しない意図も示します。

商品表示を作るC++
std::string make_label(const std::string& name, int price) {
    return name + ": " + std::to_string(price) + "円";
}

int main() {
    std::string name{"ノート"};
    std::cout << make_label(name, 180) << '\n';
}
実行結果OUTPUT
ノート: 180円

nameはコピーされず参照として渡り、constによりmake_label内からは変更できません。この例には#include <string>#include <iostream>が必要です。関数定義をmainより後ろに置く場合は、先に関数プロトタイプを宣言します。

08

例外とエラー

呼び出し側で回復可能な異常は例外で伝えられます。

安全な割り算C++
double divide(double a, double b) {
    if (b == 0) throw std::invalid_argument("0では割れません");
    return a / b;
}

try {
    std::cout << divide(10, 0) << '\n';
} catch (const std::invalid_argument& error) {
    std::cout << error.what() << '\n';
}
実行結果OUTPUT
0では割れません

#include <stdexcept>が必要です。検索結果がないなど通常起こり得る状態は、std::optionalで表す設計も検討します。

09

ファイルの読み書き

出力にstd::ofstream、入力にstd::ifstreamを使います。スコープを抜けると自動で閉じられます。

保存して読むC++
std::ofstream output{"memo.txt"};
if (!output) return 1;
output << "C++を学習中\n";
output.close();

std::ifstream input{"memo.txt"};
std::string line;
std::getline(input, line);
std::cout << line << '\n';
実行結果OUTPUT
C++を学習中

#include <fstream>が必要です。オープン成功を確認し、利用者が指定したパスで意図しないファイルを上書きしないようにします。

10

クラスとカプセル化

クラスはデータと操作をまとめます。データをprivateにし、外部へ必要な操作だけをpublicで公開します。

ProductクラスC++
class Product {
private:
    std::string name_;
    int price_;

public:
    Product(std::string name, int price) : name_{std::move(name)}, price_{price} {}
    void print() const { std::cout << name_ << ": " << price_ << "円\n"; }
};

Product product{"ノート", 180};
product.print();
実行結果OUTPUT
ノート: 180円

std::moveには#include <utility>が必要です。初期化リストはメンバーを作成時に初期化します。

11

CMakeとテスト

ファイルが増えたらCMakeでビルド手順を記述します。ソースと別のフォルダーに生成物を置くアウトオブソースビルドが一般的です。

CMakeLists.txtCMAKE
cmake_minimum_required(VERSION 3.16)
project(hello LANGUAGES CXX)
set(CMAKE_CXX_STANDARD 17)
set(CMAKE_CXX_STANDARD_REQUIRED ON)
add_executable(hello main.cpp)
ビルドCOMMAND
cmake -S . -B build
cmake --build build
ctest --test-dir build
依存関係 外部ライブラリは公開元、ライセンス、対応コンパイラ、固定バージョンを確認し、追加後にテストします。
PRACTICE

ミニ課題:在庫管理

商品名、価格、在庫数を持つProductクラスを作り、std::vector<Product>から在庫金額を計算してください。

完成条件
  • 負の価格や在庫数を受け付けない
  • 表示と計算を別の関数にする
  • -Wall -Wextraで警告がないことを確認する
NEXT

次に学ぶこと

基礎を終えたら、リソースの所有権と標準ライブラリを深く学び、安全でテストしやすいコードへ進みましょう。

C++の発展テーマ
  • STLアルゴリズム:sortfind_iftransformでコレクションを処理する
  • スマートポインタ:unique_ptrshared_ptrで寿命と所有権を表す
  • Google Test:関数やクラスの振る舞いを自動確認する
  • Boost:標準ライブラリを補う汎用ライブラリ群を必要に応じて学ぶ

まず在庫管理課題の検索や並べ替えをSTLアルゴリズムで書き換え、Google Testで通常値と境界値を確認すると、基礎から自然に発展できます。