본문 바로가기
Programming Language/Java

[Java/개념] 상속(Inheritance) 과 메소드 재정의(@Overriding)

by wo__ongii 2024. 10. 22.
728x90
반응형

자바의 상속은 객체 지향 프로그래밍의 중요한 개념으로, 기존 클래스를 확장하여 새로운 클래스를 정의하는 방법이다. 상속을 통해 코드를 재사용함으로써 중복을 줄이고 유지보수를 용이하게 할 수 있다. 상속 구조에서는 기존 클래스를 부모 클래스(상위 클래스), 상속받는 클래스를 자식 클래스(하위 클래스)라고 부른다.

 

1. 상속(Inheritance)

상속은 자식 클래스가 부모 클래스의 필드와 메소드를 물려받는 기능이다. 하지만 private 접근 제한자를 가진 필드와 메소드는 상속되지 않으며, 다른 패키지에 속하는 경우 default 접근 제한자를 가진 필드와 메소드도 상속되지 않는다.

또한 자바는 다중 상속을 허용하지 않기 때문에 자식 클래스는 extends 키워드를 사용하여 오직 하나의 부모 클래스만 상속받을 수 있다.

class 자식클래스 extends 부모클래스 {
    // 필드
    // 생성자
    // 메소드
}

2. 부모 생성자 호출

자식 클래스의 객체를 생성할 때, 자바는 부모 클래스의 생성자를 먼저 호출한 후 자식 클래스의 생성자를 호출한다. 이때의 객체 생성 순서는 아래와 같다.

  • 자식 클래스 객체 생성 요청: new 키워드를 사용하여 자식 클래스의 객체를 생성하면, 자식 클래스의 생성자가 호출된다.
  • 부모 클래스의 생성자 호출: 자식 클래스 생성자의 첫 번째 줄에서 부모 클래스의 생성자가 호출된다. 이때 명시적으로 super()를 호출하지 않으면 부모 클래스의 기본 생성자가 자동으로 호출된다.
  • 부모 클래스 필드 및 메서드 초기화: 부모 클래스의 생성자가 호출되며 부모 클래스의 필드가 초기화되고 부모의 생성자 코드가 실행된다.
  • 자식 클래스 필드 및 메서드 초기화: 부모 생성자가 완료된 후 자식 클래스의 생성자가 실행되며, 자식 클래스의 필드와 메서드가 초기화된다.
public class Car { // 부모 클래스
    public Car() {
        System.out.println("Car 객체 생성");
    }

    public void move() {
        System.out.println("차를 이동합니다.");
    }
}

public class ElectricCar extends Car { // 자식 클래스
    public ElectricCar() {
        super(); // 부모 생성자 명시적 호출
        System.out.println("ElectricCar 객체 생성");
    }

    public void charge() {
        System.out.println("충전합니다.");
    }
}

public class ExtendExample {
    public static void main(String[] args) {
        ElectricCar electricCar = new ElectricCar();
        electricCar.move();   // 부모 클래스 메서드 호출
        electricCar.charge(); // 자식 클래스 메서드 호출
    }
}

/*
실행결과:
Car 객체 생성
ElectricCar 객체 생성
차를 이동합니다.
충전합니다.
*/

3. 메소드 탐색 순서

자식 클래스에 해당 메소드가 존재하지 않으면, 자바는 부모 클래스에서 메소드를 찾는다. 부모 클래스에도 없을 경우 상위 부모 클래스에서 계속 탐색합니다. 이때 메소드를 찾지 못하면 컴파일 에러가 발생한다.

public class Car {
    public void move() {
        System.out.println("차를 이동합니다.");
    }
}

public class ElectricCar extends Car {
    // 자식 클래스에 move() 메서드가 없으므로 부모 클래스의 메서드가 호출됨
}

public class Main {
    public static void main(String[] args) {
        ElectricCar electricCar = new ElectricCar();
        electricCar.move();  // 부모 클래스의 move() 호출
    }
}

 

4. 메소드 재정의(@Override)

1) 메소드 오버라이딩(Overriding)

메소드 오버라이딩(Overriding)은 상속받은 부모 클래스의 메소드가 자식 클래스에 맞지 않을 때, 자식 클래스에서 동일한 이름의 메소드를 재정의하는 기능이다. @Override 어노테이션을 사용하여 메소드가 오버라이딩되었음을 명시적으로 표시할 수 있다.

public class Car {
    public void move() {
        System.out.println("차를 이동합니다.");
    }
}

public class ElectricCar extends Car {
    @Override
    public void move() {
        System.out.println("전기차를 빠르게 이동합니다.");
    }

    public void charge() {
        System.out.println("충전합니다.");
    }
}

public class Main {
    public static void main(String[] args) {
        ElectricCar electricCar = new ElectricCar();
        electricCar.move();  // 오버라이딩된 자식 클래스의 메서드 호출
    }
}

/*
실행결과:
전기차를 빠르게 이동합니다.
*/

 

[오버라이딩 시 주의사항]

  • 메소드 이름이 같아야 한다.
  • 메소드 매개변수의 타입, 순서, 개수가 같아야 한다.
  • 반환 타입이 같아야 한다.
  • 접근 제어자는 부모 메소드보다 더 제한적일 수 없다.
  • 오버라이딩된 메소드는 부모 클래스보다 더 많은 예외를 throws로 선언할 수 없다.
  • static, final, private 메소드는 오버라이딩할 수 없다.

 

2) 부모 메소드 호출(super)

부모와 자식 클래스에서 필드명이나 메소드가 동일할 경우, 자식 클래스에서 부모의 필드나 메소드를 호출하려면 super 키워드를 사용한다.

public class Parent {
    public String value = "parent";

    public void hello() {
        System.out.println("Parent.hello");
    }
}

public class Child extends Parent {
    public String value = "child";

    @Override
    public void hello() {
        System.out.println("Child.hello");
    }

    public void call() {
        System.out.println("this.value = " + this.value);   // 자식 클래스의 value
        System.out.println("super.value = " + super.value); // 부모 클래스의 value
        this.hello();   // 자식 클래스의 hello() 호출
        super.hello();  // 부모 클래스의 hello() 호출
    }
}

public class Main {
    public static void main(String[] args) {
        Child child = new Child();
        child.call();
    }
}

/*
실행결과:
this.value = child
super.value = parent
Child.hello
Parent.hello
*/

 

 

 

 

 

[참조: 이것이 자바다]

728x90
반응형