2022/2/17
다형성 Polymorphism
여러 가지 형태를 가질 수 있는 능력. 상속 관계에서 성립 가능한 문법.
참조형의 업/다운 캐스팅 (참조형을 형 변환하는 거처럼 보인다……)
부모 타입의 변수에 자식 객체를 집어 넣는 것.

변수보다는 메서드 때문에 다형성을 하는 것. 오버 라이딩된 메서드를 사용하게 해 주는 게 목적이다.
1. instanceof 연산자: 참조하는 변수가 가리키는 인스턴스 (객체)의 실제 타입을 체크하는 데 사용.
참조 변수 instanceof 클래스명 -> true/false
(참조변수가 클래스의 객체냐~?)
바로 위의 부모부터 조상까지 모두 true로 리턴.
내 아래 자식이나 아예 다른 클래스는 false.
추상 클래스
1. 개발할 때, 밑그림을 그리는 것. 설계 쪽에 해당. 구조를 미리 짜놓고 싶을 때.
2. 키워드: abstract
3. 추상 메서드: abstract 키워드를 붙여 메서드의 선언부만 있고, 구현부 ({코드 작성하는 곳})은 되어있지 않은 형태.
public abstract String getName();
public abstract void getName(String str);
4. 추상 클래스: 일반 멤버들과 함께 추상 메서드를 포함하는 클래스.
추상 메서드가 하나라도 있으면 무조건 추상 클래스!
이를 명시하기 위해 클래스 앞에 abstract 붙이기.
abstract class Shape {
…
abstract void draw();
}
5. 추상 클래스는 객체 생성 불가. 불완전한/ 미상인 클래스임.
Shape s = new Shape(); (x) new 객체 생성이 안 된다.
Shape s; 변수 선언하여 껍데기만 만드는 건 가능.
6. 상속에서 슈퍼 클래스로 사용된다. 부모 클래스가 될 수 있음. extends
추상 클래스를 쓰려면 부모로 놓고 상속을 받아 불완전한 추상 메서드를 오버 라이딩.
7. 추상 클래스를 물려받은 서브 클래스를 완성시키려면, 추상 메서드를 오버 라이딩해야 한다.
추상 클래스를 단순히 상속만 받은 서브 클래스는 그 또한 추상 클래스가 된다.
추상 메서드를 그대로 상속받기 때문에 구현을 하지 않는다면 클래스 앞에 abstract 키워드를 붙여줘야 한다.
#추상 클래스 단순 상속
abstract class Rect extends Shape { //추상 draw();
int width;
…
}
#추상 클래스를 사용할 때 -> 상속받아 구현 완성
class Rect extends Shape {
@Override
void draw(){
//추상 메서드 구현 코드 작성
}
}
new Rect(); // 객체 생성 가능
인터페이스 Interface: 규격. (중요!)
1. 키워드: interface
[구조]
interface PhoneInterface {
//내용……
}
객체 생성 불가. 규격만 따놓은 것.
2. 인터페이스의 멤버는 추상 메서드와 상수만으로 구성된다. (일반 변수나 일반 메서드는 못 들어감)
(추상 클래스는 추상 메서드 일반 변수 일반 메서드 들어가고 앱스트랙 키워드 필요
인터페이스는 추상 메서드와 상수만. )
interface PhoneInterface {
public static final 타입 변수 명 = 값; //상수
public abstract 리턴 타입 메서드 명(); //추상 메서드
public static final int BUTTONS= 20;
public abstract void sendCall();
public abstract void receiveCall();
}
인터페이스 멤버는 누구나 접근 가능하게 모두 public 접근 지정자로 만듦.
3. 모든 메서드는 public abstract이며 선언 시 키워드 생략 가능하다. 어차피 모두 public abstract이기 때문에..
int BUTTONS= 20;
4. 상수는 public static final이며 선언 시 키워드 생략 가능하다. 이유는 위와 동일.
객체 생성 안 해도 값은 쓸 수 있도록 변수를 static으로 선언.
void sendCall();
void receiveCall();
5. 인터페이스로 객체 생성 불가능. 메서드는 모두 구현이 전혀 안된 (미완성인) 추상 메서드이므로……
new PhoneInterface(); (불가능)
6. 인터페이스로 래퍼런스 변수 선언은 가능. 추상 클래스처럼 선언까지는 가능.
PhoneInterface iPhone; (가능)
7. 인터페이스끼리 상속 가능
인터페이스는 다른 인터페이스를 상속을 받을 수 있다.
인터페이스는 규격과 같은 것으로, 상속을 통해 기존 인터페이스에 새로운 규격을 추가한 새로운 인터페이스를 만들 수 있다.
extends 키워드 사용.
interface MobilePhoneInterface extends PhoneInterface {
void sendSMS();
void receiveSMS();
}
*추상보다 인터페이스를 더 많이 쓰는 이유: 인터페이스는 다중 상속 허용!
interface DualCameraPhoneInterface extends PhoneInterface, CameraInterface {
void makeVideo();
}
8. 인터페이스 구현 (사용하기): 인터페이스의 추상 메서드를 모두 구현한 클래스를 작성하는 것.
키워드: implements
class Iphone implements MobilePhoneInterface {
//추상 메서드 모두 구현
public void sendCall(){…} //원형에서 abstract 빼고 작성
public void receiveCall(){…} //내용물을 모르겠으면 일단 중괄호만 해놔도 에러 안남.
public void sendSMS(){…};
public void receiveSMS(){…};
//추가적으로 일반 메서드나 변수 작성해도 됨
public int getButtons(){…}
}
*추상 메서드 중 하나라도 구현을 안 하면 에러!
9. 인터페이스의 목적:
설계, 가이드라인을 만들 수 있다. 일단 규격, 가이드 라인만 먼저 만들자 싶을 때.
다형성을 실현하는 도구. 인터페이스 타입의 변수에, 구현 클래스로 생성한 객체 담을 수 있다. 인터페이스로 선언한 변수 (위에 있는거)에 클래스 구현하여 (8번) 담을 수 있다.
10. 인터페이스는 다중 구현도 가능.
class Iphone implements MobilePhoneInterface, CameraInterface {
//두 개 인터페이스로부터 물려받은 추상 메서드 전부 구현해야 함.
}