<aside> 💡 클래스 extends 클래스

클래스 implements 인터페이스

인터페이스 extends 인터페이스

상속제한
final : 더 이상 파생할 수 없음
sealed  ~  permits  : 지정한 후손에 대해서만 파생을 허가한다.
non-sealed : 제한 없이 파생시킬 수 있다.

<abstract 추상 클래스>

	추상클래스
	1.추상클래스를 가지고 있는 클래스는 abstract 예약어를 사용(메서드)
	2.추상클래스는 객체를 생성 할 수 없다(미완성 클래스 이므로)
	3.상속을 통해서만 사용한다(추상클래스는 상속을 위해 만들어진 클래스)
	4.추상메서드가 있는 추상클래스를 상속받는 하위 클래스는
	"반드시" 추상메서드를 override 해야한다

<인터페이스>

인터페이스에서는 변수를 선언하면 항상  final static 생략되어 있음
인터페이스에서 선언한 메서드는 기본적으로 추상메서드로 변환
- default 사용하면 기본 메서드 만들 수 있음
(호출은 하위클래스에서 추상클래스 구현후 호출가능)
- static 메서드 만들 수 있음 
(static 메서드는 호출 가능)
implements 인터페이스를 구현할떄 쓰는 예약어
EX)
class HandPhoneCamera extends HandPhone implements Camera
//클래스HandPhone 를 상속받는 클래스HandPhoneCamera가 
//인터페이스 Camera의  takepicture() 구현
//구현 implements //상속 extends 
interface A {}
interface B {}
interface C extends A, B {}  //인터페이스끼리는 다중상속 가능
// class G extends A, B {} //err

class D {}
class E extends D implements A, B {} //다중구현 가능

template 메서드

//흐름대로 진행

final public void run() { //흐름대로 진행하는 메서드.
		statCar();
		drive(); //추상메서드
		stop();  //추상메서드
		turnOff();
	}

</aside>

Abstract_sealed.java

abstract sealed class Language permits Java, Cpp, CSharp {} 
//Java, Cpp, CSarp 의 클래스에서만 Language {} 상속 허가 - 1번

final class Java extends Language {} //-2번
//final class Cpp extends Language {}
//final class CSarp extends Language {}
//final class python extends Language {}   //err : 1번으로 인해 상속 불가
//final class OpenJva extends Jva {} //err : 2번으로 인해 상속 불가

sealed class Cpp extends Language permits C11, C20 {} 
//sealed   permits 상속제한 //C11, C20 의 클래스에서만 Cpp{} 상속 허가

non-sealed class CSharp extends Language {} //CSharp는 제한없이 파생시킬 수 있다

//Cpp로부터는 두개의 클래스 파생 가능
final class C11 extends Cpp {} 
final class C20 extends Cpp {}

//CSharp 으로부터는 임의의 클래스 파생 가능
final class CSharpCore extends CSharp {}
package chapter11.interface_part1;

abstract sealed class Language permits Java, Cpp, CSharp {}  //abstract 추상 클래스 //sealed   permits 상속제한 
final class Java extends Language {}
sealed class Cpp extends Language permits C11, C20 {}

non-sealed class CSharp extends Language {} 

final class C11 extends Cpp {} 
final class C20 extends Cpp {}

final class CSharpCore extends CSharp {}

public class Abstract_sealed {

	public static void main(String[] args) {
		Language lang_java = new Java();
		outLanguageName(lang_java);
	}
	//다형성을 이용해 오버로딩 없이도 활용가능
	public static void outLanguageName(Language lang) {
		if (lang instanceof Java) {
			System.out.println("자바");
		}else if (lang instanceof Cpp) {
			System.out.println("C++");
		}else if (lang instanceof CSharp) {
			System.out.println("C#");
		}
	}

}

<출력결과>

자바

<풀이>

Language lang_java = new Java(); outLanguageName(lang_java); 에서 outLanguageName 메서드가 Language 타입의 매개변수를 받음

(=현재 구현된 내용에서는 Java 클래스의 인스턴스만을 인식)

즉, 메서드 구조를 보면, Java 클래스의 인스턴스인지를 체크함

AbstractTest

package chapter11.interface_part1;

abstract class Animal {
	//맴버 변수
	String name;
	
	//생성자
	Animal(String name) {
		this.name = name;
	}
	//맴버 메서드
	void alive() {
		System.out.println("생물");
	}
	//추상 메서드
	abstract void move();
}

abstract class Human extends Animal{
	Human (String name){
		super(name);
	}
	
	@Override
	void move() {
		System.out.println("두 발로 걷다");
	}
	
	abstract void play(); //abstract 없으면 오류남
	
}
	
class Student extends Human {
	Student(String name){
		super(name);
	}
	@Override
	void play() {
		System.out.println("놀다");
	}
}

class Tiger extends Animal{
	Tiger (String name){
		super(name);
	}
	
	@Override
	void move() {
		System.out.println("네 발로 걷다");
	}
	
}

class Eagle extends Animal{
	Eagle (String name){
		super(name);
	}
	
	@Override
	void move() {
		System.out.println("날다");
	}
	
}
public class AbstractTest {

	public static void main(String[] args) {

		//Animal a = new Animal(); arr발생 추상클래스는 인스턴스 생성 불가
    //Animal b = new Human("사람");
		Animal b = new Student("학생"); //상속받아서 더 큰 의미를 나타낼 수 있음 
		Animal c = new Tiger("호랑이");
		Animal d = new Eagle("독수리");
		
		b.alive();
		b.move();
		c.move();
		d.move();
		

	}

}

<출력결과>

생물 두 발로 걷다 네 발로 걷다 날다

InterfaceTest

package chapter11.interface_part1;

interface Calc { 
	//final이 생략된 상수 //질문 인터페이스에서는 변수를 선언하면 항상  final static 생략되어 있음
	double PI = 3.14; //final static 생략되어 있음
	int ERROR = -9999999;
	
	//인터페이스에서 선언한 메서드는 추상메서드로 변환
	int add(int num1, int num2); //반환값이 int인 구현체가 존재하지않는 추상메서드 //abstract 생략되어 있음
	int substract(int num1, int num2);
	int times(int num1, int num2);
	int divide(int num1, int num2);
	
	//default 메서드 //인터페이스에서는 기본적으로 추상메서드가 만들어지지만, default 사용하면 기본 메서드 만들 수 있음
	default void description() {
		System.out.println("정수 계산기를 구현합니다.");
	}
	
	//static 메서드
	static int total(int[] arr) {
		int total = 0;
		for (int i : arr) {
			total += i;
		}
		return total;
	}
	
}

abstract class Calculator implements Calc {  //interface인 Calc의 추상클래스 add, substract를 클래스 Calculator가 구현

	@Override
	public int add(int num1, int num2) {
		return num1 + num2;
	}

	@Override
	public int substract(int num1, int num2) {
		return num1 - num2;
	}

//	@Override
//	public abstract int times(int num1, int num2); //구현 x -> 생략
//	@Override
//	public abstract int divide(int num1, int num2); //구현 x -> 생략
	
}

class CompleteCalc extends Calculator { //클래스 Calculator를 상속받은 클래스CompleteCalc에서  Calculator의 추상클래스 times, divide 를 구현

	@Override
	public int times(int num1, int num2) {
		return num1 * num2;
	}

	@Override
	public int divide(int num1, int num2) {
		if (num2 != 0) return num1 / num2;
		else           return Calc.ERROR;
	}
	
	public void showInfo() {
		System.out.println("Calc 인터페이스를 구현하였습니다.");
	}
	
}

public class InterfaceTest {

	public static void main(String[] args) {
		int arr[] = {1,2,3,4,5};
		System.out.println(Calc.PI); //interface에 직접 접근
		System.out.println(Calc.ERROR);
		System.out.println(Calc.total(arr));//static 메서드
		//default 메서드 호출 불가/ static 영역에 없음 /인스턴스를 통해서만 호출가능 즉 하위클.래.스에서 추상클래스를 구현후 호출가능
		
		CompleteCalc calc = new CompleteCalc();
		int num1 = 10, num2 = 5;
		System.out.println(calc.add(num1,num2));
		System.out.println(calc.substract(num1,num2));
		System.out.println(calc.times(num1,num2));
		System.out.println(calc.divide(num1,num2));
		calc.showInfo();
		calc.description();
	}

}

<출력결과>

3.14 -9999999 15 15 5 50 2 Calc 인터페이스를 구현하였습니다. 정수 계산기를 구현합니다.