Hack and Play

プログラミングやCG、ゲーム、コンピュータのネタを投稿していくブログ。不定期更新。

最近気づいたC++のコード

2008年02月05日 | プログラミング
C言語とC++言語は親和性が高いんですが、それゆえにC++の特有の機能というのが曖昧なところが結構あります。
streamクラス関連のcoutなんかはstring型を使わなければ、stdioのprintfのほうが扱いやすいですし、抽象度が高いクラスはデータの流れが分かりづらいせいでデバッグがめんどくさいのでなかなか使うのには面倒な点があります。

そして勉強不足なのか、最近になってC++には参照型変数というのものがあることが分かりました。
記述は

型指定子& 参照型変数名
例(int& val)

という風な感じでかかれます。
これの効果は関数にポインタを使わずに参照させることが出来ます。
基本的に関数の引数や返り値に値渡しを使うとオーバーヘッドが増えてしまいます。オーバーヘッドを増やさないためにはポインタを使ってやり取りする必要がありますが、ポインタを使った場合だと参照させたいだけの場合では、内容が書き換えられる可能性があります。

int* getInt(int* val) {
*val++; //内容が変更される。
return val;
}

ポインタの場合、constを付けても無意味なので(constは型のデータを定数にするので、ポインタ型の場合はアドレスが定数化されるだけでデータの定数化まではできない)一見すると変更させない参照は用意できないように思えます。
そこで参照型変数の登場です。

int& getInt(const int& val) {
val++; //警告、またはエラーになる
return val;
}

このようにすることで、valは参照させるだけで、関数内で変更することができないように指定が出来ます。またconstをはずすとvalは関数内で変更可能になります。基本的にC++の参照型変数はconstをセットにして扱われるパターンが多いと思います。
上の例だとintでポインタのサイズと変わりませんが、これがデータが大きい構造体の場合などでは値渡しと参照渡しではかなり変わってきます。

C++の良い点はC言語のコードが流用できる点が良いですが、C言語のコードとC++のコードが混在するとコード管理の問題も出てきますから、一概に良いとも言い切れないのが問題ですね。



訂正(2/7):
ポインタ型でもconstを付けることで内容が変更されないようにできるそうです。

int* getInt(const int* val) {
*val = 10; //エラー
return val;
}

constは (const 型)でも(型 const)でも同じ効果を持ちますが、ポインタ型の場合は、(const int* もしくは int const *)はアドレス先の値を定数化し、ポインタ型 constの場合(int* const)はアドレスを定数化するみたいです。

思いっきり間違ってました。指摘ありがとうございました。

最新の画像もっと見る

1 コメント

コメント日が  古い順  |   新しい順
Unknown (uskz)
2008-02-06 09:57:28
すいません間違って1つ前のエントリにコメントしてしまいました

>ポインタの場合、constを付けても無意味
void f(int const* const p)
{
*p = 7; // error!
}
返信する

コメントを投稿

ブログ作成者から承認されるまでコメントは反映されません。