super
super는 자손 클래스에서 조상 클래스로부터 상속받은 멤버를 참조하는데 사용되는 참조변수입니다.
멤버변수와 지역변수의 이름이 같을 때 this를 붙여 구별했듯이 상속받은 멤버와 자신의 멤버와 이름이 같을 때는 super를 붙여 구분할 수 있습니다.
super와 this 비교
class SuperTest {
public static void main(String args[]) {
Child c = new Child();
c.method();
}
}
class Parent {
int x=10;
}
class Child extends Parent {
int x = 20;
void method() {
System.out.println("x=" + x);
System.out.println("this.x=" + this.x);
System.out.println("super.x="+ super.x);
}
}
위 코드를 보면 x = 10의 값을 갖는 Parent 클래스가 있고, Parent클래스를 상속받고 x 값을 20으로 초기화한 Child 클래스가 있습니다.
this로 x의 값을 호출시 Child클래스의 x 값을 출력하게 되며, super로 x의 값을 호출시 Parent 클래스의 x 값을 출력하게 됩니다.
super를 이용한 오버라이딩
class Point {
int x;
int y;
String getLocation() {
return "x :" + x + ", y :" + y;
}
}
class Point3Dtest extends Point {
int z;
String getLocation() { // 오버라이딩
return super.getLocation() + ", z :" + z; // 조상 메서드 호출
}
}
super를 이용해 getLocation() 메서드를 불러와 Point3Dtest의 getLocation()을 오버라이딩하였습니다.
super.getLocation()은 조상 클래스인 Point 클래스의 getLocation()의 반환 값 : "x :" + x + ", y :" + y 을 가져오게 됩니다.
즉, return "x :" + x + ", y :" + y + ", z :" + z; 와 똑같은 결과입니다.
super()
this()는 같은 클래스의 다른 생성자를 호출하는데 사용되지만, super()는 조상 클래스의 생성자를 호출하는데 사용됩니다.
super() 또한 this()와 마찬가지로 반드시 생성자의 첫 줄에서 호출해야 합니다.
만약 자식 클래스에서 생성자를 생성했는데 생성자의 첫 줄에 super() 가 없다면, 컴파일러는 여기에 자동으로 super();를 삽입하게 됩니다.
자세한 내용은 아래 코드를 참고하며 이해해봅시다.
super()의 사용
class PointTest {
public static void main(String args[]) {
Point3D p3 = new Point3D(1,2,3);
System.out.println("p3.x=" + p3.x);
System.out.println("p3.y="+ p3.y);
System.out.println("p3.z=" + p3.z);
}
}
class Point {
int x;
int 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) {
this.x = x;
this.y = y;
this.z = z;
}
String getLocation() {
return "x :" + x + ", y :"+ y + ", z :" + z;
}
}
위 코드를 실행 하면 조상 클래스의 생성자인 Point()를 찾을 수 없다는 에러가 발생합니다.
그 이유는 Point3D클래스의 생성자의 첫 줄이 생성자를 호출하는 문장이 아니기 때문에 컴파일러는 자동적으로 super();를 Point3D(int x, int y, int z) 아래에 추가합니다.
Point3D(int x, int y, int z) {
super(); // 자동으로 추가됨
this.x = x;
this.y = y;
this.z = z;
}
이게 왜 문제가 되냐 ?
자동으로 추가된 super()는 부모 클래스 Point의 Point() 생성자를 호출하는데 Point 클래스에 Point() 생성자가 없기 때문입니다.
- 그렇기 때문에 이 에러를 해결하기 위해선 2가지 방법이 있습니다.
- Point 클래스에 매개변수가 없는 생성자 Point()를 생성한다.
- Point3D(int x, int y, int z) 아래에 매개변수를 가진 super(x, y)를 추가해 Point(int x, int y) 생성자를 호출한다.
(변경하면 다음과 같습니다.)
Point3D(int x, int y, int z) {
super(x, y); // 조상클래스의 생성자 Point(int x, int y)를 호출.
this.z = z;
}
참고자료 : 자바의 정석3
'◼ JAVA' 카테고리의 다른 글
[Java/자바] 다형성(polymorphism)이란 ? (0) | 2022.10.22 |
---|---|
[Java/자바] 추상 클래스와 추상 메서드란 (abstract)? (0) | 2022.10.22 |
[Java/자바] 오버라이딩(overriding)이란 ? (0) | 2022.10.20 |
[Java/자바] 클래스의 관계 - 상속(is-a)과 포함(has-a) (0) | 2022.10.20 |
[Java/자바] 멤버변수 초기화 방법 (명시적 초기화, 초기화 블럭) (0) | 2022.10.20 |