![article thumbnail image](https://blog.kakaocdn.net/dn/P7Jb7/btrHjdjJrpH/AFKrvZzgI9uPkLTa3fGNok/img.jpg)
메서드에 인수를 전달하는 두가지 모드
Call by value란, 값을 호출하는 것을 의미. 매개변수로 전달받은 값을 복사하여 처리합니다. 즉 전달받은 값을 변경하여도 원본은 변경되지 않는다
Call by reference란 참조에 의한 호출을 의미. 매개변수로 전달받은 값을 직접 참조합니다. 즉 전달받은 값을 변경할 경우 원본도 같이 변경된다
그렇다면 자바의 참조형은 Call by reference일까?
결론적으로 말하자면 Call by Value이다.
자바에서 기본(Primitives) 변수는 실제 값을 저장하는 반면 비기본(Non-Primitives) 변수는 참조하는 객체의 주소를 가르키는 참조변수를 저장한다. 값과 참조 모두 Stack 메모리에 저장된다.
자바의 인수는 항상 값으로 전달된다. 메서드를 호출하는 동안 값이든 참조이든 각 인수의 복사본이 Stack 메모리에 생성되어 메서드에 전달된다. 기본형은 단순히 Stack 메모리 내부에 복사된 다음 호출 수신자 메서드에 전달된다. 참조형은 Stack 메모리의 참조는 Heap에 있는 실제 데이터를 가르킨다. 객체를 전달할 때 Stack 메모리의 참조가 복사되고 새 참조가 메서드에 전달된다.
public void whenModifyingObjects_thenOriginalObjectChanged() {
Foo a = new Foo(1);
Foo b = new Foo(1);
Assert.assertEquals(a.num,1);
Assert.assertEquals(b.num,1);
modify(a,b);
Assert.assertEquals(a.num,2);
Assert.assertEquals(b.num,1);
}
public void modify(Foo a1, Foo b1) {
a1.num++;
b1 = new Foo(1);
b1.num++;
}
class Foo {
public int num;
public Foo(int num) {
this.num = num;
}
}
위의 프로그램은 동일한 값 1을 갖는 a와b를 modify() 메소드에 전달했다. 처음에 이러한 개체는 힙 공간에서 두 개의 개별 개체 위치를 가르킨다
이러한 참조 a 및 b가 modify() 메서드에서 전달되면 동일한 이전 객체를 가르키는 참조 a1 및 b1의 복사본이 생성된다.
modify() 메서드에서 참조 a1을 수정하면 원래 객체가 변경된다. 그러나 참조 b1에 대해 새 객체를 할당했다. 이제 힙 메모리의 새 개체를 가르키고 있다. b1에 대한 모든 변경 사항은 원래 객체의 어떤 것도 반영하지 않는다.
참고
https://www.baeldung.com/java-pass-by-value-or-pass-by-reference
'자바' 카테고리의 다른 글
JVM, JDK, JRE, JIT (0) | 2022.07.18 |
---|---|
String의 특징 (0) | 2022.07.14 |
equals()와 hashCode() (0) | 2022.07.14 |