[Java] Call by Reference / Call by Value?

hyunoi·2024년 11월 21일
1

Java

목록 보기
10/20
post-thumbnail

두 가지 호출 방식


Call by Reference

참조에 의한 호출
변수의 메모리 주소를 직접 전달하는 것
만약에 전달받은 값을 변경한다면? 원본도 같이 변경된다.

Call by Value

값에 의한 호출
변수에 저장된 값을 그대로 복사하여 전달하는 것
만약에 메소드 내에서 전달받은 값을 변경한다면? 메소드 안에서만 변경되고, 원래 전달된 값은 변경되지 않는다.

자바는 Call by Value


자바에서는 두 가지 데이터형으로 분류할 수 있는데,

  • 기본형(Primitive type)
    값 자체가 복사되어서 전달
    전달된 값은 변경 불가능
    Boolean, short, int, long, float, doyble, char
  • 참조형(Reference type)
    객체의 주소 값을 복사하여 전달
    참조된 객체의 내부 상태 언제든 변경 가능
    기본형을 제외한 모든 타입들

기본형은 값 그대로가 전달되는 것이고, 참조형은 주소값이 전달되는 것이다.
결국에 둘 다 값을 전달하는 것이 된다.

그래서 자바에서는 Call by Value를 사용한다고 하는 것이다.
원시이 복사되느냐 주소이 복사되느냐 둘 중 하나이기 때문!

이때 참조형을 전달할 때 왜 Call by Value일까

예시를 들어보자

public class Main {
    public static void main(String[] args) {
        StringBuilder sb = new StringBuilder("Hello");

        // StringBuilder 객체를 메서드에 전달
        System.out.println("Before modify: " + sb);
        modifyStringBuilder(sb);  // 객체의 내용 수정
        System.out.println("After modify: " + sb);  // 객체의 내용이 수정됨
    }

    public static void modifyStringBuilder(StringBuilder sb) {
        sb.append(", World!");  // StringBuilder 내부 수정
        sb = new StringBuilder("Goodbye");  // 새로운 객체 할당, 원본 객체에는 영향 없음
    }
}

> Output
Before modify: Hello
After modify: Hello, World!

StringBuilder는 참조 타입
sb원본 객체의 주소값modifyStringBuilder에 전달된다.

이때, 주소값 자체가 복사되어서 전달된다.
그래서 메소드 내에서 객체를 변경할 수는 있지만, 기존의 주소값 자체는 변경할 수 없게 되는 것

위 코드처럼 메소드 내에서 sb를 새로운 객체로 할당하려고 해도 원본 객체가 변경되지 않고 "Hello, World"가 출력되는 것을 볼 수 있다.

결론

자바는 Call by Value
객체의 주소값이 복사되어 전달되고, 객체의 상태 수정은 가능하지만? 주소값 자체를 바꿀 수는 없다는 것에서 Call by Value 방식으로 작동한다.

0개의 댓글