ポインターをパラメーターとして受け入れる関数があるとします。この関数はstd::vector<>::push_back()
、このポインターのライフサイクルを管理するために使用するため、例外をスローできます。次のように宣言すると:
void manage(T *ptr);
次のように呼び出します。
manage(new T());
ポインタを にプッシュする例外がスローされた場合std::vector<>
、事実上メモリリークが発生していますよね?
次のように関数を宣言します。
void manage(std::auto_ptr<T> ptr);
私の問題を解決しますか?
std::auto_ptr
最初にスタックに割り当てて(例外をスローすることはできなかったと思います)、ポインターに対する所有権を取得できるようにすることを期待しています。安全。
次に、関数内で生のポインターを にプッシュしますがstd::vector<>
、これも安全です。これが失敗した場合、ポインターは追加されませんが、スマート ポインターは引き続きポインターを所有しているため、破棄されます。プッシュが成功した場合、そのポインターに対するスマート ポインターの所有権を削除して戻ります。これは例外をスローできないため、常に問題ありません。
私の理論は正しいですか?
- 編集 -
いいえ、できないと思います。これを行うには、rvalue への非 const 参照を取得する必要があります (スマート ポインターから所有権を奪うため)。私は書かなければならないだろう
std::auto_ptr<T> ptr(new T());
manage(ptr);
それが機能するためには、私の場合はかなり不便です。これを書いているのは、コードをあまり汚さずに RAII を実装できるようにするためです。そんなことをしても何の役にも立ちません。キャッチ22になります。
-- 編集 2 --
読者がすぐに参照できるように、ジェイソン・オレンドルフがここに言ったことをここに引っ張り出すと、最終的な解決策は次のようになります。
void manage(T *ptr)
{
std::auto_ptr<T> autoPtr(ptr);
vector.push_back(ptr);
autoPtr.release();
}
これにより、右辺値への無用な非 const 参照の問題が解決されます。
コーディング中のこのクラスを終了したら、誰かが役に立つと思った場合に備えて、ここに投稿します。
-- 編集 3 --
わかりました、ここで多くの議論がありましたが、以前に明確にしておくべき重要なポイントがあります。通常、stackoverflow に投稿するときは、質問の背後にある理由を説明しようとしますが、一般的に、それはまったく役に立ちません。ということで、今回は本題に入ろうと思いました。うまくいかなかったことが判明 XD
残念ながら、私の脳は今行き詰まっているので、目標を達成するために最初に考えたことを正しく説明することさえできないと思います. 多くの場合に適合するアトミック操作と例外セーフなコード作成の適切な解決策を見つけようとしていますが、実際にはそれを処理できません XD これは時間とともに習得するだけの種類のものだと思います.
私はまったく新しい C++ プログラマーで、ゲーム開発に重点を置いています。ゲームエンジンで例外がスローされると、それは実行の終了です。システムはプロセス用にすべてのメモリを解放するので、あちこちで 1 つまたは 2 つのポインターがリークしても問題ありません。サーバー アプリケーションを開発しているので、例外を処理するのが難しいと感じています。例外はサーバーをクラッシュさせることはできないからです。「リクエストをクラッシュさせる」必要があります。
つまり、「お客様、残念ながら開発者はこの状態を予測していませんでしたので、後で試していただく必要があります (ここまでは基本的にゲーム エンジンと同じで、何も修復されていないだけです。プロセス全体ではなく、リクエストのみのコンテキストに分離されます。ただし、すべてが有効な状態のままであるため、パニックにならないでください (ただし、ここに違いの 1 つがあります。プロセスは終了しないため、オペレーティング システムはリソースを解放できません。さらに、これまでの操作を元に戻すには注意が必要です。たとえば、ユーザーのアカウントを完全にロックしたり、サーバーが提供する完全なサービスをロックしたりしないようにする必要があります。 )」。
次回はより良い質問を書くことができるように、どんどんコーディングして問題を書き留めます。今さら質問する気になれませんでした、本当に申し訳ありません。
返信ありがとうございます。私はスタックオーバーフローが本当に好きです。私の質問に対する回答の速さと、あなたの回答がどれだけ啓発的であるかには、本当に驚くべきものがあります。ありがとう。