C++で参照渡しよりもポインタ渡しを選ぶメリットとは?具体例で解説
C++では、関数に大きなオブジェクトを渡したり、関数内で元の変数を書き換えたりする場合、「ポインタ渡し」と「参照渡し」という2つの方法が使えます。どちらも実質的には同じメモリ上のオブジェクトを扱いますが、言語仕様や可読性の面で重要な違いがあります。
ポインタ渡しの利点
1. nullptr(NULL)を受け取れる
ポインタは nullptr を受け取ることができます。一方、参照は必ず有効なオブジェクトに束縛されなければならず、「オブジェクトが存在しない」状態を表現できません。したがって、「何もない」ことを引数として渡したいケースでは、ポインタを使うしかありません。
2. 呼び出し側で渡し方がひと目でわかる
ポインタ渡しでは、呼び出し側で明示的にアドレス演算子 & を付けて引数を渡します。そのため、呼び出し箇所を見るだけで、そのオブジェクトが参照(ポインタ)として渡されているのか、値渡しなのかを判別できます。参照渡しの場合、構文上は値渡しとまったく同じに見えるため、関数の定義を確認しない限り実際の挙動はわかりません。
ポインタ渡しの例
次のコードは、ポインタを使って2つの整数の値を入れ替える(スワップする)例です。
#include <iostream>
using namespace std;
void swap(int* a, int* b) {
int c = *a;
*a = *b;
*b = c;
}
int main() {
int m = 7, n = 6;
cout << "Before Swap\n";
cout << "m = " << m << " n = " << n << "\n";
swap(&m, &n);
cout << "After Swap by pass by pointer\n";
cout << "m = " << m << " n = " << n << "\n";
}
出力結果
Before Swap
m = 7 n = 6
After Swap by pass by pointer
m = 6 n = 7
参照渡しの例
同じ処理を参照渡しで書くと、次のようになります。関数本体も呼び出し側も、より簡潔に記述できることがわかります。
#include <iostream>
using namespace std;
void swap(int& a, int& b) {
int c = a;
a = b;
b = c;
}
int main() {
int m = 7, n = 6;
cout << "Before Swap\n";
cout << "m = " << m << " n = " << n << "\n";
swap(m, n);
cout << "After Swap by pass by reference\n";
cout << "m = " << m << " n = " << n << "\n";
}
出力結果
Before Swap
m = 7 n = 6
After Swap by pass by reference
m = 6 n = 7
まとめ
両者の実行結果は同じですが、使い分けのポイントは次のとおりです。
- ポインタ渡し: 引数として「オブジェクトなし(nullptr)」を許容したい場合や、呼び出し側で渡し方を明示したい場合に適しています。
- 参照渡し: 必ず有効なオブジェクトが存在することが保証されており、構文もシンプルになるため、null を許さない場面ではこちらが推奨されます。
現代のC++では、null の可能性がないなら参照渡しを基本とし、null を許容する必要がある場合のみポインタ(または std::optional などの代替手段)を使うのが一般的なスタイルとされています。
-
C++のキーワード(予約語)は全部で何個?グループ別に解説
C++には合計95個の予約語(キーワード)が定義されています。これらの予約語は、由来や用途ごとにいくつかのグループに分けて考えると、とても覚えやすくなります。 グループ1:C言語から引き継がれた予約語(32個) 最初のグループは、Cプログラミング言語にも元々存在していたキーワードです。C++はCをベースに開発された言語であるため、int、if、for、while、structなど、Cからそのまま引き継がれた予約語が32個あります。 グループ2:C++で新たに追加された予約語(30個) 次のグループは、Cには存在しなかった、C++ならではの予約語です。class、new、delete、tem
-
Javaに存在しないC++の機能一覧|両言語の主な違いを徹底解説
はじめにC++とJavaはどちらも広く使われているプログラミング言語ですが、設計思想が大きく異なるため、C++に存在する機能の一部はJavaには意図的に取り入れられていません。Javaは安全性・簡潔さ・プラットフォーム非依存性を優先し、複雑さの原因となる機能を削ぎ落とした言語です。本記事では、Javaに存在しない代表的なC++機能を一覧形式でわかりやすく解説します。Javaに存在しないC++の主な機能1. 符号なし整数型(unsigned int)Javaには符号なし整数型が用意されておらず、すべての整数型(byte、short、int、long)は符号付きです。ビット操作などで符号なしの挙動