私は現在、C++ で関数を使用してオブジェクトを操作する方法を学習しています。これまでのところ、次の点に到達しています。
オブジェクトが潜在的に大きい場合は、それをローカル変数にしないでください。つまり、コピーの時間を節約するためにヒープに保持してください。
具体的には、以前には存在しなかったオブジェクトを作成する関数を使用しているシナリオに興味があります。関数がある場合に何をすべきかを示すために、次の小さな例をまとめました。
#include <iostream>
using namespace std;
struct obj {
int first;
int second;
};
void setFirstVersionA(int a, obj * s)
{
s->first = a;
}
obj * setFirstVersionB(int a)
{
//in Version B I am creating a new object in the function but have to run delete outside
obj * s = new obj();
s->first = a;
return s;
}
int main(int argc, const char** argv)
{
obj * myobj = new obj();
setFirstVersionA(2,myobj);
//now I have the new obj in *i
cout << myobj->first;
delete myobj;
//this is an alternative to passing a pointer directly:
//no need to re-declare the pointer as delete only erases the myobj data
myobj = setFirstVersionB(3);
//now I have the new obj in *i
cout << myobj->first;
delete myobj;
return 0;
}
私が知る限り、両方の関数で同じ結果が得られます。
バージョン A の方が、new 宣言と delete 宣言が分離されておらず、完了後にオブジェクトを削除するのを忘れる可能性が低くなるため、私はバージョン A の方が気に入っています。しかし、それは戻り型 void であり、関数が何をするかを実際に確認する必要があるため (一般的には、他のファイルを読み取ることを意味します)、コードが読みにくくなっています。
私が変更したかった「もの」を返すので、バージョン B の方が好きです。したがって、この関数はその人 (この場合は obj ) を変更することがすぐにわかります。ただし、新規と削除を分離します。正直なところ、コードに一連の void 関数があり、それらが何をするかをすぐに確認しないよりもひどいことではありません。また、ここではローカル変数へのポインターを返さないことについて多くのことが書かれていますが、バリアント B では、オブジェクトは関数内で作成されますが、ローカル変数ではありません (ヒープにあるため)。右?
それを行うより良い方法はありますか?また、「以前には存在しなかったオブジェクトを作成する関数」は、コンストラクターのように聞こえます。:) おそらく、オブジェクトごとにコンストラクターを持つクラスを作成する必要がありますか?
アドバイスありがとうございます!