프로그래밍/Java

자바 프로그래밍 / extends와 implements 차이

배기니어 2021. 2. 10. 19:22

지난 자바 프로그래밍에서 추상클래스와 인터페이스의 차이에 대해 알아보았다.

 

2021/02/05 - [프로그래밍/Java] - 자바 프로그래밍 / 추상클래스와 인터페이스의 차이

 

자바 프로그래밍 / 추상클래스와 인터페이스의 차이

지난 안드로이드 소켓 프로그래밍에서 쓰레드를 이용해 서버에 접속하려고 할 때, 쓰레드 클래스를 상속하여 새로운 MyThread라는 클래스를 생성하였다. 2021/01/31 - [프로그래밍/Android Java] - 안드로

bagineer.tistory.com

 

그렇다면 작성된 코드 중 extends와 implements라는 키워드가 보였을 것이다.

 

(보셨죠??)

 

public class ManInCar extends Vehicle implements Run {
 
	public ManInCar(double max_vel, int cc) {
		super(max_vel, cc);
	}
 
	@Override
	public void run(double vel) {
		// TODO Auto-generated method stub
		System.out.println("Current velocity : " + vel);
	}
 
	@Override
	public void start() {
		// TODO Auto-generated method stub
		System.out.print("Press brake pedal > ");
		System.out.print("insert key > ");
		System.out.print("turn the key > ");
		System.out.println("Engine started");
	}
}

 

여기서 Vehicle은 추상클래스였고, Run은 인터페이스였다.

run 메소드는 Run 인터페이스에 작성한 추상메소드였고, start 메소드는 Vehicle 클래스에서 작성한 추상메소드였다.

두 메소드를 보면 @Override라는 어노테이션(annotation)이 달려있는데, 이는 메소드를 다시 정의하겠다는 뜻이다.

두 메소드가 모두 추상메소드이다보니 내용이 없어 다시 정의할 필요가 있기 때문에 @Override가 자동으로 붙는다.

 

 


 

extends와 implements

 

여기까지는 간단한 복습이었고, 이제 extends와 implements를 알아보자.

extends 뒤에는 Vehicle이라는 클래스가 적혀있고, implements 뒤에는 Run이라는 인터페이스가 적혀있다.

그렇다면 extends는 클래스와 관련된 것이고, implements는 인터페이스와 관련된 것이라는 것을 알 수 있다.

 

그렇다!

extends는 부모 클래스를 상속하기 위한 키워드이고, implements는 구현할 인터페이스를 불러오기 위한 키워드이다.

지난 글에서 본 내용을 떠올리면 자바에서 클래스는 다중 상속이 불가능하지만 인터페이스는 여러 개를 불러올 수 있다고 했다.

따라서 extends 뒤에는 하나의 클래스만 작성해야하며, implements 뒤에는 여러 개의 인터페이스를 작성해도 된다.

 

간단한 예시를 통해 확인해보자.

지난 글에서 작성한 Car 클래스와 Run 인터페이스를 재활용하겠읍니다.

그리고 추가로 Man 클래스와 Play 인터페이스를 작성했어유~~

활용하고자 하는 클래스와 인터페이스는 아래와 같다.

 

public class Car extends Vehicle {
	
	public Car(double max_vel, int cc) {
		super(max_vel, cc);
	}

	@Override
	public void start() {
		// TODO Auto-generated method stub
		System.out.print("Press brake pedal > ");
		System.out.print("insert key > ");
		System.out.print("turn the key > ");
		System.out.println("Engine started");
	}
}

public interface Run {
	public abstract void run(double vel);
}

public class Man {

	private int age;
	private String name;
	
	public Man(int age, String name) {
		this.age = age;
		this.name = name;
	}
	
	public void introduce() {
		System.out.println(this.name + " is " + this.age + "years old.");
	}
}

public interface Play {

	public abstract void play();
	public abstract void stop();
	public abstract void puase();
}

 

이제 위의 클래스와 인터페이스를 활용해 새로운 클래스 ManInCar를 생성해보자!

차 안에 사람이 있으니 Man과 Car 두 클래스를 상속해야 하고, 웬지 extends Car, Man 이렇게 작성해야 할 것 같다.

하지만 그렇게 작성하여 ManInCar 클래스를 작성하려고 하면

 

그림 1. 두 개의 클래스 상속

 

위와 같이 syntax 에러가 발생한다.

구문 자체가 틀렸다는 것이다. 앞서 설명한 대로 두 개의 클래스를 상속하려고 해서 발생하는 에러이다.

 

그렇다면 Car 클래스만 상속하고, Run, Play 인터페이스를 구현하여 작성해보자!

extends Car implements Run, Play를 이용하면 된다.

 

package myPackage;

public class ManInCar extends Car implements Run, Play {

	public ManInCar(double max_vel, int cc) {
		super(max_vel, cc);
	}

	@Override
	public void play() {
		System.out.println("play music.");		
	}

	@Override
	public void stop() {
		System.out.println("stop music.");		
	}

	@Override
	public void puase() {
		System.out.println("pause music.");
	}

	@Override
	public void run(double vel) {
		System.out.println("current velocity : " + vel);
	}
}

 

이 클래스는 문제 없이 작성할 수 있다.

Run과 Play 인터페이스의 모든 메소드들 앞에 @Override가 붙어 재정의된 것도 확인할 수 있다.

 

 


 

요약

 

extends : 클래스 상속을 위해 사용하는 키워드

 - 하나의 클래스만 상속 가능

 - 두 개 이상의 클래스 상속을 시도하면 syntax 에러 발생

 

implements : 인터페이스 구현을 위해 사용하는 키워드

 - 여러 개의 인터페이스를 불러올 수 있음

 - 불러온 인터페이스의 모든 메소드를 재정의해서 사용해야 함