본문 바로가기

지식/Java

[Java] Call by value, Call by reference

Call by value : 값에 의한 호출

- 함수가 호출될 때 메모리 공간 안에서는 임시의 공간이 생성됩니다. 그리고 함수가 종료되면 해당 공간은 사라집니다.

- 함수 호출 시 전달되는 변수 값을 복사해서 함수 인자로 전달합니다.

- 복사된 인자값은 함수에서만 지역적으로 사용되기 때문에 local value 속성을 가집니다.

 

* 즉, 함수 안에서 인자값이 변경되어도, 외부 변수 값은 변경되지 않습니다.

(데이터 값을 복사해서 함수로 전달하기 때문에 원본 데이터가 변경될 가능성이 없습니다.)

 

 

Call by reference : 참조에 의한 호출

- 함수 호출 시 전달되는 변수의 레퍼런스를 전달합니다.

- 인자값은 전달된 변수를 가르키게 되어 인자값을 변경할 경우 전달된 변수의 값도 변경되게 됩니다.

 

* 즉, 함수 안에서 인자값이 변경되면, 외부 변수 값도 동일하게 변경됩니다.

 

 

Java 함수 호출 방식

Java는 항상 call by value로 값을 넘깁니다.

C/C++처럼 변수의 주소값 자체를 가져올 방법이 없으며, 이를 넘길 수 있는 방법 또한 있지 않습니다.

reference type(참조 자료형)을 넘길 시에는 해당 객체의 주소값을 복사하여 이를 가지고 사용합니다.

 

따라서 원본 객체의 프로퍼티까지는 접근이 가능하나, 원본 객체 자체는 변경할 수 없습니다.

 

예제를 보면

public class Test{
    public static void swap(int a, int b){
    	int temp = a;
        a = b;
        b = temp;
    }

	public static void main(String[] args){
    	int a = 1;
        int b = 2;
        
        System.out.println(a + " "+ b); // 1 2
        swap(a,b);  
        System.out.println(a + " "+ b); // 1 2
    }
}

기본적인 swap메소드로 변경 하고 출력할 경우 swap이 실행되지 않습니다.

 

그 이유는 a,b 는 기본 자료형(int,char...등) 으로 Call by value 이기 때문입니다.

 

 

그렇다면 Integer 즉 참조 자료형으로 하면 어떻게 될까요?

public class main{
    public static void swap(int a, int b){
    	Integer temp = a;
        a = b;
        b = temp;
    }

	public static void main(String[] args){
    	Integer a = 1;
        Integer b = 2;
        
        System.out.println(a + " "+ b); // 1 2
        swap(a,b);  
        System.out.println(a + " "+ b); // 1 2
    }
}

결과는 그대로..입니다..

 

그 이유는 참조 자료형을 넘길 시에는 해당 객체의 주소값을 복사하여 이를 가지고 사용합니다.

즉, 원본 객체의 프로퍼티까지는 접근이 가능하나, 원본 객체 자체를 변경할 수는 없습니다.

 

** Java에서 Call by reference는 해당 객체의 주소값을 "직접" 넘기는 것이 아닌 객체를 보는 또 다른 주소값을 만들어서 넘겨줍니다.

 

 

참고

 

https://devlog-wjdrbs96.tistory.com/44

https://github.com/gyoogle/tech-interview-for-developer/blob/master/Language/%5Bjava%5D%20Call%20by%20value%EC%99%80%20Call%20by%20reference.md