コンテンツにスキップ

E.A.2 C++ 応用

C++ RAII と所有権マップ

デプロイで出てくる C++ 応用の中心は、ほとんどこの問いです。誰がリソースを所有し、いつ解放するのか。

所有権とインターフェースの例を動かす

Section titled “所有権とインターフェースの例を動かす”

advanced.cpp を作成します。

#include <iostream>
#include <memory>
struct Engine {
virtual ~Engine() = default;
virtual float run(float input) = 0;
};
struct CpuEngine : Engine {
float run(float input) override {
return input * 0.84f;
}
};
class Session {
public:
explicit Session(std::unique_ptr<Engine> engine)
: engine_(std::move(engine)) {}
void predict() {
std::cout << "cpu_score=" << engine_->run(1.0f) << "\n";
std::cout << "session_done\n";
}
private:
std::unique_ptr<Engine> engine_;
};
int main() {
Session session(std::make_unique<CpuEngine>());
session.predict();
return 0;
}

実行します。

Terminal window
c++ -std=c++17 advanced.cpp -o advanced
./advanced

期待される出力:

Terminal window
cpu_score=0.84
session_done
C++ の要素デプロイでの意味
Engine インターフェースビジネスコードが CPU/GPU/runtime backend を切り替えられる
std::unique_ptr1 つの所有者だけが engine リソースを管理する
std::move所有権を Session に移す
virtual ~Engine()インターフェース経由でも安全に片付けられる
RAIIリソース寿命がオブジェクト寿命に従う

AI システムでこの形がよく出る理由

Section titled “AI システムでこの形がよく出る理由”

推論システムでは、同じ業務経路を別の backend に差し替えることがあります。CPU fallback、GPU runtime、量子化 engine、remote service wrapper などです。呼び出し側は backend の詳細ではなく、Engine を実行できればよいはずです。

この例では責務を 3 つに分けています。

  • Engine は契約を定義する。
  • CpuEngine は 1 つの実装を提供する。
  • Session は 1 つの engine を所有し、契約越しに呼び出す。

所有権が曖昧だと、デプロイの不具合は追いにくくなります。メモリが漏れる、buffer が runtime より長く残る、片付け順序がずれる、といった問題です。std::unique_ptr と RAII は、寿命をコメントではなく型で見えるようにします。

2 つ目の engine を追加します。

struct FastEngine : Engine {
float run(float input) override {
return input * 0.91f;
}
};

それから CpuEngineFastEngine に置き換えます。Session の他のコードは変えないでください。

操作例と確認ポイント

FastEngine は同じ Engine インターフェースを実装します。そのため Session 側では、構築時に別のオブジェクトを渡すだけで済みます。

Session session(std::make_unique<FastEngine>());

重要なのは、SessionCpuEngine そのものではなくインターフェースに依存していることです。std::unique_ptr により所有権が明確になり、session が 1 つの engine インスタンスを所有し、終了時に自動的に解放されます。

このページを終えたら、この証拠カードを残します。

デプロイ先
ローカル推論、エッジデバイス、モデルサーバー、または最適化実験
成果物
C++ スニペット、ベンチマーク、model artifact、serving 設定、または deployment メモ
指標
レイテンシ、メモリ、スループット、モデルサイズ、accuracy 低下、または信頼性
失敗確認
ABI/ビルドの問題、ハードウェア不一致、量子化損失、または配信ボトルネック
期待される成果
理論メモだけでなく、再現可能なデプロイまたは最適化の証拠

Session が engine を所有する理由、ここで unique_ptr が raw pointer より安全な理由、インターフェースで runtime backend を差し替えられる理由を説明できれば合格です。