[Java] 심화 - 제네릭(Generic)

이지연·2025년 12월 25일

개요

아래의 내용은 java_grammer 레파지토리 C06EtcClass 디렉터리에 저장되어있는 내용을 정리함

  • C04GenericMain
    제네릭 개요 → 배열 교환 → 컬렉션 활용 워크플로우

제네릭이란?

제네릭은 클래스나 메서드의 타입을 파라미터화해서, 객체 생성할 때마다 다양한 타입으로 지정 가능하게 해주는 거야.
코드 재사용성 향상이 핵심. 타입 안전성도 보장해주고.

제네릭 없는 코드 문제점

String[] stArr = {"java", "python", "c++"};
stChange(stArr, 0, 1);  // String용 메서드 따로

Integer[] inArr = {10, 20, 30};
intChange(inArr, 0, 1); // Integer용 메서드 따로

문제: 배열 요소 교환하려면 타입마다 메서드 따로 만들어야 함. 코드 중복 심각.

제네릭 메서드 해결

static <T> void allChange(T[] arr, int a, int b) {
    T temp = arr[a];
    arr[a] = arr[b];
    arr[b] = temp;
}

사용법

allChange(stArr, 1, 2);  // String[] 자동 추론
allChange(inArr, 1, 2);  // Integer[] 자동 추론

문법 포인트

  • 반환타입 왼쪽에 <T> 선언
  • T참조형 객체만 허용 (int, double 같은 기본형 X)
  • 클래스에 <T> 있으면 메서드에서 생략 가능

실행 결과

[java, python, c++]  // 교환 전
[java, c++, python]  // stArr 교환 후
[10, 20, 30]         // 교환 전
[10, 30, 20]         // inArr 교환 후

제네릭 클래스 사용

class GenericPerson<T> {
    private T value;
    
    public GenericPerson(T value) { this.value = value; }
    public T getValue() { return value; }
}

다양한 타입 사용

GenericPerson<String> p1 = new GenericPerson<>("hong");   // T=String
GenericPerson<Integer> p2 = new GenericPerson<>(20);      // T=Integer

System.out.println(p1.getValue()); // hong
System.out.println(p2.getValue()); // 20

실무 컬렉션에서 제네릭

List<String> myList = new ArrayList<>();     // ArrayList<E>
Map<String, Integer> myMap = new HashMap<>(); // HashMap<K,V>
Optional<Student> myStudent;                 // Optional<T>

ArrayList 들어가보면 ArrayList<E> 제네릭 확인 가능.
실무 99%는 이런 컬렉션 제네릭으로 타입 안전성 확보.

제네릭 한계점

제한사항설명대안
기본형 불가GenericPerson<int> XWrapper 클래스 (Integer)
타입 소거런타임에 제네릭 정보 사라짐리플렉션 한계

정리

  • 제네릭 메서드: <T>로 타입 파라미터화 → 코드 중복 제거
  • 제네릭 클래스: <T>로 다양한 타입 객체 생성
  • 실무: List<String>, Map<K,V> 형태로 99% 사용

제네릭 없었으면 ArrayList마다 StringList, IntegerList 따로 만들어야 했음
타입 안전성 + 재사용성이 제네릭의 핵심 가치

profile
Eazy하게

0개의 댓글