[Java] 07. 상속

JK·2024년 4월 14일
0

[Java]

목록 보기
7/11

상속 개념

상속(Inheritance)은 부모가 자식에게 물려주는 행위를 말한다. 자바에도 상속의 개념이 존재하는데, 부모 클래스가 본인의 필드와 메소드를 자식 클래스에게 물려주는 것이다.

상속을 사용하면 하나는 이미 잘 개발된 클래스를 재사용해서 새로운 클래스를 만들기 때문에 중복되는 코드를 줄여서 개발 시간을 단축시킬 수 있다. 또한 클래스의 수정을 최소화할 수 있다는 이점도 있다.

클래스 상속

public class 자식클래스 extends 부모클래스 {
}

프로그램에서의 상속은 자식이 부모를 선택한다. 자식 클래스를 선언할 때 extends 뒤에 상속을 받을 클래스를 명시하여 어떤 부모로부터 상속을 받을 것인지를 결정한다.

부모 생성자 호출

// 자식 생성자 선언
public 자식클래스(...) {
  super(매개값, ...);
  ...
}

상속을 받은 자식 객체를 생성하면 부모 객체가 먼저 생성된다. 자식 생성자의 맨 첫 줄에 숨겨져 있는 super()에 의해 부모 생성자가 호출되어 부모 객체를 생성한 후에 자식 객체를 생성한다.

super()는 컴파일 과정에서 자동 추가되고, 매개변수가 없는 부모의 기본 생성자를 호출한다. 따라서 부모 클래스에 기본 생성자가 없다면 컴파일 에러가 발생한다. 부모 클래스에 기본 생성자가 없다면 직접 super(매개값, ...) 코드를 이용해서 직접 부모 생성자를 호출해야 한다.


메소드 재정의

메소드 오버라이딩(Overriding)은 자식 클래스가 사용하기에 적합하지 않게 설계된 부모 클래스의 메소드를 자식 클래스에서 재정의(오버라이딩)하여 사용하는 것이다. 오버라이딩된 메소드는 기존 부모 클래스의 메소드보다 우선적으로 사용된다.

메소드를 오버라이딩할 때 @Override 어노테이션을 사용하면 컴파일 단계에서 정확히 오버라이딩이 되었는지 체크해준다.

메소드 오버라이딩 시 주의할 점

  1. 부모 메소드의 선언부(리턴 타입, 메소드 이름, 매개변수)와 동일해야 한다.
  2. 접근 제한을 더 강하게 오버라이딩할 수 없다.
  3. 새로운 예외를 throws 할 수 없다.

재정의된 메소드의 부모 메소드 호출

메소드를 재정의할 경우, 부모 메소드는 숨겨지고 재정의된 메소드만 사용되기 때문에, 부모 메소드와 중복되는 코드도 자식 메소드에서 별도로 가지고 있어야 한다.

super.method();

super 키워드와 도트(.) 연산자를 사용한다면 숨겨진 부모 메소드를 호출해서 중복된 코드를 작성하는 과정을 없앨 수 있다.


final 클래스와 final 메소드

final 클래스는 클래스 선언 시 final 키워드를 붙여 최종적인 클래스로 만든 것이다. 즉, 더 이상 해당 클래스는 자식 클래스를 만들 수 없다.

final 메소드는 메소드 선언 시 final 키워드를 붙여 최종적인 메소드로 만든 것이다. 즉, 더 이상 재정의(오버라이딩)할 수 없다. 만약 클래스에서 자식 클래스를 만들더라도 해당 자식 클래스에서 부모의 final 메소드는 더 이상 재정의할 수 없다.

타입 변환

타입 변환은 타입을 다른 타입으로 변환하는 것으로, 클래스에서도 타입 변환이 발생할 수 있다. 하지만 클래스의 타입 변환은 상속 관계에 있는 클래스 사이에서만 발생한다.

자동 타입 변환

자동 타입 변환은 자식 타입 객체가 부모 타입 객체로 변환될 때 발생한다. 자식 객체는 부모 객체의 특징과 기능을 상속받기 때문에 부모와 동일하게 취급할 수 있다.

만약 바로 위의 부모가 아니더라도 상속 계층에서 상위 타입 해당하는 객체라면 자동 타입 변환이 발생한다. 부모 타입으로 자동 타입 변환된 이후에는 부모 클래스에 선언된 필드와 메소드만 접근할 수 있다.

자식 클래스에서 오버라이딩된 메소드가 있다면 자동 타입 변환 후에도 오버라이딩된 메소드가 호출된다. 이 특성을 이용해 다형성을 구현할 수 있다.

강제 타입 변환

자식타입 변수 = (자식타입) 부모타입객체;

부모 타입을 자식 타입으로 변환하고 싶을 경우, 캐스팅 연산자로 강제 타입 변환을 할 수 있다. 하지만 강제 타입 변환은 모든 경우에 가능한 것이 아니라 자식 객체 타입이 부모 객체 타입으로 자동 변환된 이후, 다시 자식 객체 타입으로 변환하고 싶을 때만 가능하다.


다형성

다형성은 사용 방법은 동일하지만 실행 결과가 다양하게 나오는 성질을 말한다. 객체 사용 방법이 동일하다는 것은 동일한 메소드를 가지고 있다는 것을 의미한다. 다형성은 자동 타입 변환과 메소드 재정의를 통해 구현할 수 있다.

필드 다형성

필드 타입은 동일하지만 대입되는 객체가 달라져서 실행 결과가 다양하게 나오는 것을 필드 다형성이라고 한다. 여기서 필드 타입은 부모 객체의 타입이어야 한다.

부모 객체 타입을 상속하는 여러 자식 객체에서 부모 메소드를 재정의하면 자식 객체마다 해당 메소드의 실행 결과가 달라진다. 이 자식 객체를 부모 객체 타입의 필드에 대입할 경우 필드 타입으로 자동 변환되지만 재정의된 메소드는 기존 부모의 메소드보다 우선 실행되기 때문에 어떤 자식 객체를 대입하느냐에 따라 실행 결과가 달라질 수 있다.

매개변수 다형성

다형성은 필드보다 메소드를 호출할 때 더 많이 발생한다. 메소드에서의 다형성은 매개변수를 통해 이루어진다.

메소드에서 매개변수로 자식 객체를 제공할 경우, 매개변수로 대입된 자식 객체는 부모 객체 타입으로 자동 타입 변환되지만 메소드는 재정의된 메소드를 사용한다. 따라서 매개변수로 주어지는 자식 객체에 따라 실행 결과가 달라지게 된다.

객체 타입 확인

boolean result = 객체 instanceof 타입;

메소드의 매개변수로 자식 객체가 주어졌을 때, 부모 객체 타입으로 자동 타입 변환된 객체가 실제로 어떤 자식 객체 타입이었는지 확인하고 싶다면 instanceof 연산자를 사용할 수 있다. 좌항의 객체가 우항의 타입이면 true, 아니면 false를 리턴한다.

보통 부모 객체 타입으로 자동 타입 변환된 자식 객체를, 다시 자식 객체 타입으로 강제 타입 변환하기 위해 사용한다. 자식 클래스에만 사용하는 필드나 메소드를 사용하고 싶다면 다시 자식 객체 타입으로 되돌려야 하기 때문이다.

java 12 버전 부터는 instanceof 연산의 결과가 true 이면 좌항의 객체를 우항의 타입으로 강제 타입 변환하지 않아도, 우항 타입 변수를 사용할 수 있다.


추상 클래스

객체를 생성할 수 있는 클래스를 실체 클래스라고 한다면, 실체 클래스들의 공통적인 필드나 메소드를 추출해서 모아 만든 클래스는 추상 클래스라고 한다.

이렇게 만들어진 추상 클래스는 new 연산자를 통해 객체를 직접 생성할 수는 없고, 새로운 실체 클래스를 만들기 위한 부모 클래스로만 사용된다.

추상 클래스 선언

public abstract class 클래스명 {
  // 필드
  // 생성자
  // 메소드
}

클래스 선언에 abstract 키워드를 붙이면 추상 클래스 선언이 된다. 추상 클래스도 필드, 메소드를 선언할 수 있고, 부모 클래스이기 때문에 생성자도 반드시 있어야 한다.

추상 메소드와 재정의

abstract 리턴타입 메소드명(매개변수, ...);

추상 클래스에서는 메소드 선언부(리턴타입, 메소드명, 매개변수)만 동일하고 실행 내용은 자식 클래스마다 달라야 하는 경우가 많다. 이 경우 위와 같이 실행 내용을 가지지 않는 추상 메소드를 선언할 수 있다.

추상 메소드는 자식 클래스의 공통 메소드라는 것만 정의할 뿐, 실행 내용을 가지지 않는다. 그렇기 때문에 자식 클래스에서 반드시 재정의(오버라이딩)해서 실행 내용을 채워야 한다.

봉인된 클래스

public sealed class Person permits Employee, Manager { ... }

Java 15 버전부터 무분별하게 자식 클래스를 생성하는 것을 방지하기 위해 도입된 기능이다. 봉인된 클래스는 sealed 키워드 사용하여 선언하며 permits 키워드 뒤에 상속 가능한 자식 클래스를 지정해야 한다.

봉인된 클래스를 상속하는 클래스는 final 또는 non-sealed 키워드를 사용하거나, sealed 키워드로 또 다른 봉인 클래스로 선언한다. final은 더 이상 상속할 수 없다는 의미, non-sealed는 봉인을 해제한다는 의미이다.


"한빛 미디어 출판 도서, 이것이 자바다"를 읽고 학습한 내용을 토대로 작성되었습니다.

0개의 댓글