Daily Dev Q&A: 오버로딩과 오버라이딩

2025. 12. 5. 08:50·Archive/Daily Dev Q&A

Topic (오늘의 주제)

오버로딩(Overloading)과 오버라이딩(Overriding)

자바의 다형성을 구현하는 두 가지 핵심 방법으로, 이름은 비슷하지만 동작 시점(컴파일 vs 런타임)과 목적(확장 vs 재정의)이 완전히 다른 개념입니다.


Why (왜 사용하는가? 왜 중요한가?)

이 개념이 실무, 설계, 면접에서 중요한 이유를 정리한다.

  • 실무:
    • (오버로딩) 이 기능이 없으면 printInt, printString 처럼 인자 타입마다 함수 이름을 다르게 지어야 하는 '작명 지옥'에 빠집니다.
    • (오버라이딩) 부모 클래스에서 물려받은 기능이 자식 클래스에 맞지 않을 때, 이를 수정할 수 없어 유연한 상속 사용이 불가능해집니다.
  • 구조적 의미: 정적 바인딩(오버로딩)을 통한 효율성과 동적 바인딩(오버라이딩)을 통한 유연성이라는 상반된 최적화 가치를 제공합니다.
  • 면접 의도: 지원자가 단순히 용어의 차이를 아는 것을 넘어, "컴파일 타임 다형성"과 "런타임 다형성"의 바인딩 시점 차이를 정확히 이해하고 있는지 확인합니다.

Core Concept (핵심 개념 정리)

요소 오버로딩 (Overloading) 오버라이딩 (Overriding)
개념 정의 같은 이름의 메소드를 매개변수만 다르게 하여 **여러 개 정의(확장)**하는 것. 상위 타입(부모 클래스 또는 인터페이스)의 메소드를 하위 타입에서 **재정의(구현)**하는 것.
동작 방식 정적 바인딩 (Static Binding): 컴파일 시점에 매개변수 타입을 보고 호출할 메소드가 결정됨. 동적 바인딩 (Dynamic Binding): 런타임 시점에 실제 생성된 객체 타입을 보고 메소드가 결정됨.
장점 메소드 이름을 통일하여 코드의 가독성을 높이고 사용성을 개선함. 부모의 코드를 수정하지 않고 자식 클래스의 특성에 맞게 기능을 변경/확장 가능 (다형성 구현).
필요 조건 1. 메소드 이름이 같아야 함.

2. 매개변수의 개수 또는 타입이 달라야 함.

3. 리턴 타입은 상관없음.
1. 메소드 이름, 매개변수, 리턴 타입이 모두 같아야 함.

2. 접근 제어자는 부모보다 좁을 수 없음.

3. 예외는 부모보다 많이 선언할 수 없음.
비교 키워드 New (새로 추가) Change (변경)

Interview Answer Version (면접 답변식 요약)

"오버로딩과 오버라이딩은 모두 다형성을 지원하지만 적용 시점과 목적이 다릅니다.

오버로딩은 같은 이름의 메소드를 매개변수만 다르게 정의하는 것으로, 컴파일 시점에 결정되며 가독성을 높여줍니다.

반면 오버라이딩은 상속받은 메소드를 재정의하는 것으로, 런타임 시점에 실제 객체에 따라 실행될 메소드가 결정되어 유연한 설계를 가능하게 합니다."


Practical Tip (사용시 주의할 점 or 활용 예)

1. 실무 활용 코드 비교

Java
 
class Printer {
    // [오버로딩] 편의성 제공: 무엇이든 출력 가능
    void print(int a) { System.out.println("숫자: " + a); }
    void print(String b) { System.out.println("문자: " + b); }
}

class Parent {
    void move() { System.out.println("걷는다"); }
}

class Child extends Parent {
    // [오버라이딩] 기능 변경: 자식의 상황에 맞게 수정
    @Override // 실무 필수: 컴파일러에게 검사를 맡김
    void move() { System.out.println("달린다"); } 
}

2. 주의할 점 ("이걸 모르고 사용하면 생기는 문제")

  • 오버로딩의 모호성 (Ambiguity):
    • void method(int a, long b)와 void method(long a, int b)가 있을 때 method(10, 10)을 호출하면 컴파일 에러가 발생합니다. (컴퓨터가 어느 것을 호출할지 모름)
  • 오버라이딩 시 @Override 생략 금지:
    • 이를 생략하고 메소드명을 실수로 다르게 적으면(오타), 컴파일러는 오류를 내지 않고 "새로운 메소드를 만들었구나(오버로딩/추가)"라고 판단하여 치명적인 버그를 만듭니다.
  • 접근 제어자 규칙 위반:
    • 부모가 protected인 메소드를 자식이 private으로 오버라이딩할 수 없습니다. (더 좁아질 수 없음)

예상 꼬리질문 정리

  1. 리턴 타입만 다르게 해서 오버로딩을 할 수 있나요?
    • 답변 키워드: 불가능합니다. 오버로딩은 오직 '매개변수의 구성'으로만 식별합니다. 리턴 타입만 다르면 컴파일 에러(Duplicate method)가 발생합니다.
  2. private 혹은 static 메소드도 오버라이딩이 가능한가요?
    • 답변 키워드: 불가능합니다. private은 상속되지 않아 자식이 볼 수 없고, static은 클래스 레벨에 고정되므로 런타임 다형성(오버라이딩)의 대상이 아닙니다. (static은 Hiding이라 함)
  3. 자바의 '공변 리턴 타입(Covariant Return Type)'이란 무엇인가요?
    • 답변 키워드: 오버라이딩 시 리턴 타입을 부모 메소드 리턴 타입의 '하위 클래스'로 변경하는 것은 허용된다는 규칙입니다. (예: 부모가 Object 반환 → 자식이 String 반환 가능)

공부하며 몰랐던 개념 (Deep Dive)

단순히 "된다/안 된다" 문법만 외우는 것이 아니라, **"왜 이렇게 설계되었으며, 실무 코드 품질에 어떤 영향을 주는가?"**를 이해하는 것이 핵심이다.

 

① 공변 리턴 타입 (Covariant Return Type): "형변환(Casting) 지옥 탈출"

  • 기존의 상식: 오버라이딩을 하려면 리턴 타입이 부모와 토씨 하나 틀리지 않고 똑같아야 한다고 배웠다.
  • 문제 상황: 팩토리 패턴(Factory Pattern) 등을 쓸 때, 부모 타입으로 리턴 받으면 매번 **다운 캐스팅(Down Casting)**을 해야 하는 번거로움이 있었다.
  • 해결 (Java 5+): "자식은 부모의 일종이다"라는 대원칙(LSP)에 따라, 리턴 타입을 '자식 클래스'로 좁혀서 반환하는 것을 허용하게 되었다.

[❌ 공변 리턴 타입 미사용 (Old Style)] 클라이언트가 매번 형변환을 해야 해서 코드가 지저분하고 불안함.

    • Java
       
      class Factory {
          public Object create() { return new Object(); }
      }
      
      class CarFactory extends Factory {
          @Override
          public Object create() { // 리턴 타입을 부모와 똑같이 Object로 유지
              return new Car();
          }
      }
      
      // 실무 사용 시 불편함
      Factory factory = new CarFactory();
      Car myCar = (Car) factory.create(); // 😫 매번 (Car)로 형변환 필수!

      [✅ 공변 리턴 타입 적용 (Modern Style)] 메서드 선언부만 봐도 무엇이 반환되는지 명확하며, 형변환 코드가 사라짐.

    • Java
      class CarFactory extends Factory {
          @Override
          public Car create() { // 😎 리턴 타입을 더 구체적인 'Car'로 변경!
              return new Car();
          }
      }
      
      // 실무 사용 시 깔끔함
      CarFactory factory = new CarFactory();
      Car myCar = factory.create(); // 😍 형변환 없이 바로 Car 객체로 사용 가능
      

      ② 생성자 (Constructor): "덮어쓰기(Override)가 아니라 이어달리기(Chain)"

      • 초보자의 오해: "메서드도 오버라이딩 되니까, 생성자도 부모 맘에 안 들면 오버라이딩해서 바꾸면 되는 거 아냐?"
      • 설계의 본질: 생성자는 **'객체를 탄생시키는 과정'**이다. 자식 객체가 태어나려면(생성되려면) 반드시 부모 객체의 뼈대부터 먼저 만들어져야 한다. 즉, 부모의 생성 과정을 덮어버리는(Override) 게 아니라, 부모의 생성을 먼저 호출하고(super) 내 것을 덧붙이는 구조여야 한다.

      [🔍 구조적 이유: 이름 불일치] 오버라이딩의 전제 조건은 **'메서드 이름이 같아야 한다'**이다.

      • 부모 클래스 생성자 이름: Parent()
      • 자식 클래스 생성자 이름: Child()
      • 애초에 이름이 다르므로 오버라이딩 성립 자체가 불가능하다.

      [💡 실무 적용: 생성자 오버로딩의 활용] 오버라이딩은 안 되지만, **오버로딩(Overloading)**은 객체 생성의 편의성을 위해 적극 사용된다

      public class User {
          private String name;
          private String role;
      
          // ① 기본 생성자 (필수값 없음)
          public User() {
              this.name = "Guest";
              this.role = "MEMBER";
          }
      
          // ② 이름만 아는 경우 (오버로딩)
          public User(String name) {
              this.name = name;
              this.role = "MEMBER";
          }
      
          // ③ 관리자 생성 시 (오버로딩)
          public User(String name, String role) {
              this.name = name;
              this.role = role;
          }
      }

결론 (Lesson Learned)

  1. 공변 리턴 타입을 적극 활용하면, 클라이언트 코드(내 코드를 사용하는 곳)에서 불필요한 형변환((Type))을 제거하여 코드 안전성을 높일 수 있다.
  2. 생성자는 상속과 재정의의 대상이 아니라, 호출의 순서(super())와 초기화의 다양성(Overloading) 관점에서 바라봐야 한다.

'Archive > Daily Dev Q&A' 카테고리의 다른 글

Daily Dev Q&A: 자바의 Collections Framework  (0) 2025.12.08
Deily Dev Q&A: SOLID원칙  (0) 2025.12.08
Daily Dev Q&A: 다형성  (0) 2025.12.03
Daily Dev Q&A: 상속과 컴포지션(Composition)의 차이와, 언제 컴포지션을 사용하는가?  (0) 2025.12.02
Daily Dev Q&A: 객체지향언어란? & 왜 JAVA가 객체지향언어인가?  (0) 2025.12.01
'Archive/Daily Dev Q&A' 카테고리의 다른 글
  • Daily Dev Q&A: 자바의 Collections Framework
  • Deily Dev Q&A: SOLID원칙
  • Daily Dev Q&A: 다형성
  • Daily Dev Q&A: 상속과 컴포지션(Composition)의 차이와, 언제 컴포지션을 사용하는가?
tlsgkstj
tlsgkstj
짱구의 성장 일기
  • tlsgkstj
    코딩하는 짱구
    tlsgkstj
  • 전체
    오늘
    어제
    • 분류 전체보기 (159)
      • About (1)
      • Projects (35)
        • Personal Projects (21)
        • Team Projects (14)
      • Engineering (20)
        • CS & Tools (0)
        • Backend Core (15)
        • Frontend (1)
        • Infra & Cloud (2)
        • AI & Tools (1)
      • Trouble Shooting & Issues (0)
      • Growth & Career (38)
        • Interview Prep (0)
        • Retrospectives (38)
      • Archive (65)
        • TIL (8)
        • Daily Dev Q&A (56)
  • 블로그 메뉴

    • 홈
    • About
    • Projects
    • Tech Stack
    • Dev Log
    • GitHub
  • 링크

    • github
  • 공지사항

  • 인기 글

  • 태그

    Spring비교
    OrphanRemova
    프로덕트개발자
    SpringBoot
    커리어리셋
    경기기후바이브코딩
    java
    jpa
    aws_s3
    Project_Review
    데브페스트
    devlog
    프로젝트회고
    spring
    backend
    network
    REACT
    DevFestIncheon2025
    클로드코드
    til
  • 최근 댓글

  • 최근 글

  • hELLO· Designed By정상우.v4.10.5
tlsgkstj
Daily Dev Q&A: 오버로딩과 오버라이딩
상단으로

티스토리툴바