読者です 読者をやめる 読者になる 読者になる

山崎屋の技術メモ

IT業界で働く中で、気になること、メモしておきたいことを書いていきます。

javaのオブジェクトは「参照の値渡し」

java

オブジェクト編です。

話はそれますが、プリミティブ型の反対は参照型というらしいのですが、
今回のテーマの中で「参照型」って言葉を使うと、混乱するので、「オブジェクト」にしています。

本題。
よく「javaではすべて値渡し」って説明を初心者にしている人を見ますが、ちょっと不親切な気がします。
間違ってはいないけど、丁寧に「参照の値渡し」と教えてあげましょう。

それでは、サンプルです。

メインクラスとは別に、メソッドの引数でやり取りするためのクラスを宣言しておきます。

public class Obj {
	public int a;
}

メインクラス

public class Argument {
	public static void main(String[] args) {
		Obj o = new Obj();
		o.a = 2;
		methodA(o);
		System.out.println("oが持つ変数aの内容は[" + o.a + "]");
	}

	private static void methodA(Obj b) {
		b.a = 3;
	}
}

実行結果

oが持つ変数aの内容は[3]

ただ、これだけだと「なんだ、参照渡しじゃん」と言われます。

なので、メインクラスをちょっと変えて、これも見せてやります。

public class Argument {
	public static void main(String[] args) {
		Obj o = new Obj();
		o.a = 2;
		methodA(o);
		System.out.println("oが持つ変数aの内容は[" + o.a + "]");
	}

	private static void methodA(Obj b) {
		b = new Obj();
		b.a = 3;
	}
}

実行結果

oが持つ変数aの内容は[2]

または、こう↓。

public class Argument {
	public static void main(String[] args) {
		Obj o = new Obj();
		o.a = 2;
		methodA(o);
		System.out.println("oが持つ変数aの内容は[" + o.a + "]");
	}

	private static void methodA(Obj b) {
		b = null;
	}
}

実行結果

oが持つ変数aの内容は[2]


つまり、参照そのものを渡しているのではなく、参照をコピーしてから渡しているのです。
なので、「参照の値渡し」と理解しておくのが良いと思います。

ちなみにC++でオブジェクトの値渡しというと、オブジェクトをまるまるコピーしてから渡すので、C++経験者に対して「javaはすべて値渡し」っていうと、思いっきり勘違いされそうな気がします。

即戦力にならないといけない人のためのJava入門(Java 8対応) エンタープライズシステム開発ファーストステップガイド (CodeZine BOOKS)

即戦力にならないといけない人のためのJava入門(Java 8対応) エンタープライズシステム開発ファーストステップガイド (CodeZine BOOKS)

やさしいJava 第5版 (「やさしい」シリーズ)

やさしいJava 第5版 (「やさしい」シリーズ)