* 상속
- 자바에서 상속이란 부모 클래스의 멤버를 자식 클래스에게 물려주는 행위이다.
- 프로그램에서는 자식 클래스가 부모 클래스를 선택하며 클래스명 뒤에 “extends 부모 클래스명“를 기술하여 사용한다.
- 단, 다중 상속은 허용하지 않는다.
class 자식클래스명 extends 부모클래스1, 부모클래스2 --> 절대 X
- 다른 패키지의 클래스를 상속할 경우 패키지명.클래스명을 import해야한다.
* 상속의 장점
- 상속은 이미 개발된 클래스를 재사용하여 새로운 클래스를 만들기 때문에 코드의 중복을 줄여준다.
- 상속을 이용하여 클래스의 수정을 최소화할 수 있다. 즉, 유지 보수 시간을 최소화한다.
package sec.example;
public class A {
int field1;
void method1() { ... }
}
public class B extends A { //A를 상속함
String field2;
void method2() { ... }
}
* 상속 가능 범위
- 부모 클래스에서 private 접근 제한을 갖는 멤버들(필드와 메소드)은 상속 대상에서 제외된다.
- 부모 클래스와 자식 클래스가 서로 다른 패키지일 때 부모 클래스의 default 접근 제한을 갖는 멤버들도 상속 대상에서 제외된다.
- 그 외에 상속한 클래스의 필드와 메소드는 자식 클래스에서 자유롭게 사용할 수 있다.
B b = new B();
//A로부터 물려받은 필드와 메소드
b.field1 = 10;
b.method1();
//B가 추가한 필드와 메소드
b.field2 = "홍길동“;
b.method2();
* 부모 생성자의 호출
- 자식 객체를 생성하면, 부모 객체가 먼저 생성되고 그 다음에 자식 객체가 생성된다. 마치, 부모 없는 자식이 없는 것처럼 말이다.
- 부모 생성자는 자식 생성자의 맨 첫줄에서 super() 키워드를 통해 호출된다. 생성자가 명시적으로 선언되지 않았다면 컴파일러는 디폴트 생성자에 super(); 키워드를 맨 앞에 추가하여 생성해 낸다. 여기서 super(매개변수); 는 부모 생성자 역할을 한다.
- super의 매개변수는 부모 생성자의 매개변수의 형태와 동일해야한다.
* 메소드의 재정의(Overriding)
- 어떤 메소드는 상속받은 자식 클래스에서 사용하기에 부적합할 수도 있다. 이 문제를 해결하고자 상속된 일부 메소드는 자식 클래스에서 다시 수정해서 사용할 수 있다. 즉, 자식 클래스에서 부모 클래스의 메소드와 동일한 메소드를 재정의하는 것을 말한다.
- 재정의할 메소드 위에는 @Override 키워드가 있어야 한다.
- 메소드가 오버라이딩되면 부모 객체의 메소드는 숨겨지기 때문에 자식 객체에서 메소드를 호출하면 오버라이딩된 자식 객체가 호출된다.
- 그러나 간혹, 숨겨진 부모 객체의 메소드를 사용해야 할 때가 있다면, super 키워드를 이용하여 호출할 수 있다.
super.부모메소드();
- 메소드 오버라이딩 규칙
- 부모의 메소드와 동일한 구조(리턴 타입, 메소드 이름, 매개 변수 리스트)를 가져야 한다.
- 접근 제한을 더욱 강하게 오버라이딩 할 수 없다.
- (상속된 부모 객체의 메소드가 default일 때 private로 바꿀 수 없으며, public으로는 가능하다.)
- 새로운 예외(Exception)를 throws 할 수 없다.
* final 클래스와 final 메소드
- 상속할 수 없는 final 클래스 : 클래스 선언 시 아래와 같이 class 앞에 final 키워드를 붙이게 되면 이 클래스는 최종적인 클래스이므로 상속할 수 없는 클래스가 된다. 즉, final 클래스는 부모 클래스가 될 수 없다.
public final class 클래스명 { ... }
- 오버라이딩(Overriding)할 수 없는 final 메소드 : 메소드를 선언할 때 final 키워드를 붙이게 되면 이 메소드는 최종적인 메소드가 되므로 오버라이딩할 수 없는 메소드가 된다. 즉, 부모 클래스에서 상속해서 자식 클래스를 선언할 때 부모 클래스에 선언된 final 메소드는 자식 클래스에서 재정의할 수 없다.
public final 리턴타입 메소드(매개변수) { ... } //해당 메소드 재정의 불가
* protected 접근 제한자
- 부모 클래스의 멤버가 protected 접근 제한자를 가질 경우 자식 클래스는 다른 패키지라도 부모 객체의 필드, 생성자, 메소드를 사용할 수 있다.
- 생성자의 경우, 부모 객체를 new 연산자로 생성하는 것이 아니라 자식 클래스의 생성자에서 super(); 키워드를 통해서 호출할 수 있다.
* 타입 변환과 다형성
- 다형성은 하나의 타입에 여러 객체를 대입하여 이용할 수 있는 성질을 말한다. 이러한 다형성을 위해 자바는 자식 클래스에서 부모 클래스로 자동 타입 변환하는 것을 허용한다. 즉, 부모 타입에는 모든 자식 객체가 대입될 수 있다.
만약 Car 클래스를 상속하는 SportCar 클래스가 있다면,
SportCar mySportCar = new SportCar();
Car myCar = mySportCar; //자동 타입 변환
mySportCar 변수와 myCar 변수는 타입만 다를 뿐 동일한 객체(SportCar)를 참조한다.
- 매개 변수의 타입이 클래스일 경우, 해당 클래스의 객체 외에 상속받는 자식 객체까지도 매개값으로 사용할 수 있다.
- 단, 부모 타입으로 자동 타입 변환된 이후에는 부모 클래스에 선언된 필드와 메소드만 접근할 수 있다. 즉, 변수는 자식 객체를 참조하더라도 해당 변수로 접근 가능한 멤버는 부모 클래스의 멤버로 제한된다.
- 그러나 메소드가 자식 클래스에서 오버라이딩 되었다면 부모 타입으로 자동 타입 변환되어도 오버라이딩된 메소드가 호출된다.
- 바로 위의 부모 클래스가 아니더라도 상속 계층에서 상위 타입이라면 하위 타입이 자동 타입변환 된다.
- 강제 타입 변환(Casting) : 자식 타입이 부모 타입으로 자동 변환한 후, 다시 자식타입으로 변환할 때 강제 타입 변환을 해야 한다. 즉, 부모 타입에 부모 객체가 아닌 자식 객체가 있는 경우에 가능하다.
자식클래스 변수 = (자식클래스) 부모클래스;
* 객체 타입 확인
- 강제 타입 변환은 자식 타입이 부모 타입으로 변환되어 있는 상태에서만 가능하므로 부모 타입의 변수가 부모 객체를 참조할 경우 자식 타입으로 변환할 수 없다.
- instanceof : 위의 문제점을 해결하고자 어떤 객체가 어떤 클래스의 인스턴스(객체)인지 확인하는데 사용되는 연산자이다.
boolean result = 좌항(객체) instanceof 우항(타입);
- 해당 타입이면 true, 아니면 false를 리턴한다.
// Child extends Parent
// Child -> Parent (자동타입변환)
// Parent -> Child (캐스팅)
public void method(Parent parent) {
Child child1 = new Child();
Parent parent = child1;
//parent 변수가 참조하는 객체는 Child 클래스의 인스턴스(객체)인가?
if(parent instanceof Child) {
Child child = (Child) parent
}
}
'Programming Language > JAVA' 카테고리의 다른 글
11. Array - 배열 (0) | 2017.04.16 |
---|---|
10. Abstract Class - 추상 클래스 (0) | 2017.04.08 |
8. 클래스의 구성 멤버와 접근 제한자 (0) | 2017.04.08 |
7. Class and Object - 클래스와 객체 (+ 쓰레기 수집) (0) | 2017.04.06 |
6. About Java and Exception - 예외 (0) | 2017.03.31 |