조종 다음은 개발
article thumbnail

개요

https://github.com/woowacourse/back-end-roadmap/blob/master/Images/backend_roadmap_v1.2.3.png

우테코 프리코스기간이 끝난 뒤에 어떤걸 공부하면 좋을까 생각하다가 우테코 로드맵을 확인하게 되었다.

이 중에서 Varargs 가 있었는데, 이게 무엇인지 잘 몰랐다...

그래서 이번 기회에 정리하게 되었다.

🫥 가변인자(Varargs)란?

가변인자란 JDK 5 부터 도입된 기능으로, 필요에 따라 매개변수 개수를 가변적으로 조절하는 기능이다.

무슨말인지 잘 이해가 안될 수도 있다.

백문일불여일견, 바로 확인해보자.

 

가변인자를 활용하지 않는 예시

int sum(int a, int b) {
    return a + b;
}

매개변수를 2개 받아서 합을 반환하는 매우 간단한 함수를 정의했다.

그런데 여기서 만약 매개변수를 3개 받는 함수도 필요하게 된다면 어떨까?

int sum(int a, int b) {
    return a + b;
}

int sum(int a, int b, int c) {
    return a + b + c;
}

똑같은 기능을 하는 함수를 매개변수만 추가해주어 오버로딩 해야할 것이다.

그런데 또 요구사항이 추가되어 4개 받는 함수가 필요한 경우에는, 5개는?? 10개는??

매번 필요할때 마다 오버로딩해야한다면 여간 귀찮은 일이 아닐 수 없다.

그래서 등장한 것이 가변인자이다.

 

가변인자를 활용한 예시

가변인자를 활용하게 된다면 하나의 함수를 선언하는 것만으로 가변하는 매개변수에 대응할 수 있다.

int sum(int... a) {
    int result = 0;
    for (int num : a) {
        result += num;
    }
    return result;
}

위와 같이 가변인자를 활용하여 선언하게 된다면

아래와 같이 활용할 수 있다.

sum(1, 2);            // 3
sum(1, 2, 3, 4);        // 10
sum(1, 2, 3, 4, 5)        // 15

 

🧐 어떻게 동작할까??

int... 와 같이 변수타입... 의 형태로 매개변수를 선언하게 되면 가변인자를 활용하게 되어서

컴파일 타임에 해당 타입의 변수들을 배열로 변환해준다.

따라서 위 코드는 컴파일 단계에서 아래와 동일하게 바뀌게 된다.


외부에서 sum(1, 2, 3, 4) 와 같이 호출한 코드를 컴파일 단계에서 자동으로 4개의 요소가 들어있는 int[] 로 바꾸어서 넘겨주게 되는 것이다. 즉 매번 해당 함수가 호출될 때 마다, 해당 매개변수로 넘겨준 변수가 들어있는 배열을 생성해서 넘겨주게 되는 것이다.

 

🤪 그렇다면 언제 사용할까??

그렇다면 이런 가변인자를 언제 활용할까??

가장 많이 활용된 부분은 아마 String.format 일 것이다.

 

실제로 String.format 정의 부분을 확인해보면 아래와 같이 가변인자를 활용한 것을 볼 수 있다.

우리도 모르게 가변인자를 활용해왔었다.. ㅎㅎ

String.format 과 유사하게 System.out.printf 에서도 가변인자를 활용한다.

 

🚨 가변인자를 사용할 때 주의할 점

그렇다면 가변인자는 만능일까?? 

물론 아니다. 가변인자를 사용할 때 주의할 점을 살펴보자.

 

🏋️ 성능 이슈

위에서 설명했듯이 가변인자를 사용하게 된다면 컴파일 단계에서 가변인자를 배열로 바꿔주는 작업이 발생한다.

즉, 가변인자를 활용하는 함수가 호출될 때 마다 배열로 바꿔주는 작업이 발생하는 것이다.

그렇기 오버로딩에 비해 성능이 상대적으로 떨어질 수 밖에 없다.

 

이러한 이유로 우리가 자주 사용하는 List.of 나 Map.of 를 확인해보면 실제로 가변인자를 활용하는 것이 아닌 오버로딩을 통해 모든 매개변수의 경우의 수를 정의해두었다.

List.of가 정의된 부분

자바 개발자들에게 잘 알려진 '이팩티브 자바'에서도 "가변인자를 신중히 사용하라" 라고 나와있다.

따라서 매개변수가 유동적으로 변하는 경우가 아니라면 가변인자 대신 오버로딩을 활용하는 것이 성능상 더 좋은 선택이 될 수 있다.

 

🌗 가변인자는 항상 마지막에 선언해야한다.

가변인자를 선언할 때는 항상 맨 마지막(뒤쪽)에 선언되어야 한다.

그렇지 않다면, 에러가 발생한다.

 

😳 매개변수가 0개 들어와도 문제가 발생하지 않는다.

위와 같이 가변인자를 활용한 함수를 호출할 때 아래와 같이 매개변수를 건내지 않아도 전혀 문제가 발생하지 않는다.

왜냐하면 가변인자는 0개 이상이면 되기 때문이다.

 

따라서 만약 아무것도 건내지 않았을 때 에러가 발생하게 해주고 싶다면 아래와 같은 추가적인 조치가 필요하다.

 

🌐 Reference

https://velog.io/@kasania/Varargs%EC%97%90-%EB%8C%80%ED%95%9C-%EA%B4%80%EC%B0%B0

 

[Java] Varargs에 대한 관찰

가변인자라고 부르는 Varargs 또한 JDK 5에서 도입된 기능이다. 이 Varargs는 필요에 따라 매개변수의 개수를 가변적으로 조정할 수 있는 기능이다.

velog.io

https://ktko.tistory.com/entry/%EC%9E%90%EB%B0%94-%EA%B0%80%EB%B3%80%EC%9D%B8%EC%9E%90Varargs%EC%97%90-%EB%8C%80%ED%95%B4%EC%84%9C

 

자바 가변인자(Varargs)에 대해서

자바 1.5에서 가변 인자 메서드(Variable arity method)라고 부르는 varargs 메서드가 추가되었다. 이 메서드는 지정된 자료형의 인자를 0개 이상 받을 수 있다. 가변인자가 없었다면 컬렉션이나 배열을

ktko.tistory.com

 

profile

조종 다음은 개발

@타칸

포스팅이 좋았다면 "좋아요❤️" 또는 "구독👍🏻" 해주세요!