오버라이딩(Overriding)
조상 클래스로부터 상속받은 메서드의 내용을 변경하여 사용하는 것.
class Point{
int x;
int y;
String getLocation(){
return "x :" + x + ", y :" + y;
}
}
class Point3D extends Point{
int z;
String getLocation(){ // 오버라이딩
//return "x :" + x + ", y :" + y + ", z :" + z;
return super.getLocation() + ", z :" + z;
}
}
위의 예제처럼, 부모 클래스의 메서드를 자손 클래스에서 자신에 맞게 변경하여 사용할 수 있다.
오버라이딩을 사용하기 위한 조건은 다음과 같다.
오버라이딩의 조건
1. 조상의 메서드와 자손의 메서드의 선언부가 일치해야한다. (이름, 매개변수, 리턴타입)
2. 접근 제어자는 조상 클래스의 메서드보다 좁은 범위로 변경할 수 없다.
3. 조상클래스의 메서드보다 많은 수의 예외를 선언할 수 없다.
4. 인스턴스 메서드를 static 메서드로 또는 그 반대로 변경할 수 없다.
참조변수 super
super는 상속 받은 조상 클래스 인스턴스의 주소가 저장 된다.
this와 마찬 가지로 조상의 멤버와 자신의 멤버를 구별하는데 사용된다.
오버라이딩 시, 메서드 앞에 참조변수 super를 사용하여 조상의 메서드를 호출할 수도 있다.
조상 클래스의 생성자 super()
this()와 마찬가지로 super()는 생성자이며, 조상 클래스의 생성자를 호출하는 것이다.
생성자는 this() 또는 super()를 반드시 생성자의 첫줄에서 호출 해야한다.
그렇지 않으면 컴파일러는 자동으로 조상의 생성자에 해당하는 super()를 삽입한다.
class PointTest{
public static void main(String args[]){
Point3D p3 = new Point3D(1,2,3);
}
}
class Point{
int x, y;
Point(int x, int y){
this.x = x;
this.y = y;
}
String getLocation(){
return "x :" + x + ", y :" + y;
}
}
class Point3D extends Point{
int z;
Point3D(int x, int y, int z){
//super(); 조상의 생성자 호출
this.x = x;
this.y = y;
this.z = z;
}
String getLocation(){
return "x :" + x + ", y :" + y + ", z :" + z;
}
}
컴파일 에러 발생
예제에서는 이러한 점들을 확인할 수 있다.
생성자가 명시되어 있지 않아, 컴파일러가 자동으로 Point3D 생성자에 super()를 추가하였다.
Point 클래스에는 기본 생성자가 정의되어 있지 않은 상태로 다른 생성자가 명시되어있어,
기본 생성자가 없는 상태이다.
Point3D 생성자에서 Point의 기본 생성자를 호출하여 에러가 발생한 케이스이다.
이처럼 생성자에 의한 컴파일 에러를 방지하기 위해서 평소에 기본 생성자를 정의해두는 습관을 기르는 것이 좋다.
에러를 해결하기 위해서 2가지 방법이 있다.
1. Point 클래스의 기본 생성자를 정의한다.
2. Point3D의 생성자에서 Point(int x, int y)를 호출하도록 코드를 추가한다.
class Point3D extends Point{
int z;
Point3D(int x, int y, int z){
super(x,y);
this.z = z;
}
String getLocation(){
return "x :" + x + ", y :" + y + ", z :" + z;
}
}
1번 방법으로도 해결이 가능하지만 조상의 멤버는 조상의 생성자에서 초기화하는 것이 바람직 하므로,
2번의 방법을 사용하여 오류를 해결하는 것이 좀 더 좋은 코드라고 할 수 있다.
오버라이딩 vs 오버로딩
메서드의 형태로 보자면 구현부만 보면 된다.
오버로딩은 부모 클래스의 메서드와 비교하였을 때, 구현부가 다르고
오버라이딩은 이름, 매개변수가 리턴타입이 일치해야하므로 구현부가 같다고 할 수 있다.
다만 '오버라이딩', '오버로딩' 단어의 형태 만으로 연상을 하는 것에 혼동이 많이 오는 상태인데..
자바의 정석 책에서는
오버라이딩은 기존에 있는 것을 사용하는 것이고, 오버로딩은 새로이 만들어내는 것이라고 생각하면 된다고 한다..
이걸로는 잘 연상이 되지 않아서 나 같은 경우는
overriding > ride 탄다. > 부모의 등에 자식이 업혀있다. 를 연상해서 (오버라이딩은 상속 관계에 성립하므로)오버라이딩
overloading 과적하다. > 같은 메서드에 여러 가지를 싣는다는 느낌으로 오버로딩
이렇게 외워보려고 한다.
'Java > 자바의 정석 3판' 카테고리의 다른 글
객체지향 프로그래밍(2) - 다형성 (0) | 2023.01.25 |
---|---|
객체지향 프로그래밍(2) - 접근 제어자 (0) | 2023.01.25 |
객체지향 프로그래밍(2) - 클래스 간의 관계 설정 (1) | 2022.12.26 |
객체지향 프로그래밍(1) - 변수의 초기화 (0) | 2022.12.24 |
객체지향 프로그래밍(1) - 생성자(Constructor) (0) | 2022.12.11 |