[Java] 인터페이스(Interface)와 추상클래스(Abstract) 차이
오늘은 Interface와 Abstract의 차이에 대해서 알아볼 것이다.
비슷하면서도 다른 이 둘 어떤 차이가 있을까?
추상클래스(Abstract)
먼저 추상 클래스를 정의하는 코드를 보자
abstract class 클래스명 {
abstract 메서드명();
}
추상 클래스는 위와 같이 abstract를 class 앞에 붙여서 사용한다.
추상클래스는 전체적으로 구체적인 구성이 되어 있지 않고 설계만 되어있는 클래스라고 정의할 수 있다.
하나 이상의 추상 메서드를 포함하는 클래스를 가리켜 추상 클래스(abstract class)라고 한다.
추상클래스 특징
-
클래스 안에 메서드 중에서 한개라도 추상메서드가 있다면 해당 클래스는 반드시 abstract 클래스로 표기 되어야 하며 abstract와 final은 동시 표기 불가하다.
-
일반적인 메서드도 있을 수 있고 추상 메서드가 있을 수도 있으며 추상 클래스도 인터페이스처럼 추상 클래스가 아닌 클래스에서 상속을 받는다면 추상 메서드가 있을 경우 모두 구현해줘야 한다. (물론 추상클래스에서 추상 클래스를 상속 받는다면 모두 구현하지 않아도 된다.)
-
추상클래스는 생성자를 가질 수 있다. 추상클래스는 인스턴스를 만들 수 없지만 추상 클래스를 상속받은 클래스를 통하면 인스턴스화가 가능하다.
-
extends를 사용해서 상속 받는다.
-
추상 클래스의 궁극적인 목적은 상속을 위함이다
인터페이스(Interface)
interface 클래스명 {
public static final 변수명 = 값;
public abstract 메소드명(매개변수);
}
인터페이스는 상속하는 클래스들에서 해당 메서드들의 내용을 구현해서 사용해야 하는 메서드들의 집합이다.
추상메서드의 추상화 정도를 업그레이드 한 것이라고 볼 수 있다.
인터페이스 특징
-
인터페이스에 새로운 메서드를 추가한다고 하고 그 아래에 인터페이스로부터 상속되는 클래스가 있다면 새로운 메서드에 대한 내용을 반드시 구현해야 한다. 인터페이스 안의 모든 메서드들은 추상 메서드(abstract)이다.
-
인터페이스는 final을 붙일 수 없고 인터페이스 변수들은 static이어야 한다. 즉 인터페이스는 일반 변수를 가질 수 없고 상수만 가질 수 있다.
-
인터페이스는 생성자를 가질 수 없다. 인터페이스는 인스턴스를 만들 수 없지만 인터페이스를 구현한 클래스를 통해 인스턴스화가 가능하다.
-
접근 지정자가 아예 없거나 public 이거나 아님 abstract만 가능하다.
-
하나 이상의 인터페이스를 상속할 수 있다.
-
implements를 사용해서 상속 받는다.
인터페이스와 추상클래스 차이
-
추상클래스와 인터페이스는 둘 다 인스턴스화 하는 것이 불가능하다.
-
인터페이스의 경우 모든 변수가 기본적으로 static final이고 모든 메서드가 public abstract인 반면에, 추상클래스는 static이나 final이 아닌 필드를 지정할 수 있고 public, protected, private 메서드를 가질 수 있다.
-
인터페이스를 구현하는 클래스의 경우 다른 여러개의 인터페이스를 다중 상속하는 것이 가능하지만, 추상 클래스의 경우 상속을 통해 구현이 가능하므로 다중 상속이 불가능하고 다른 클래스에서 또 상속을 받을 수 없다.
적절한 사용 상황
추상클래스
-
공통된 개념을 표현할 경우(ex 동물이라는 추상클래스에 추상메서드 구현하여 말이라는 객체에 상속)
-
관련성이 높은 클래스 간 코드 공유할 경우
-
추상 클래스를 상속받은 클래스들이 공통으로 가지는 메서드와 필드가 많거나 public 이외에 접근제어자가 필요한 경우
-
non-static, non-final 필드 선언이 필요한 경우
인터페이스
-
구성 요소들이 자주 바뀌는 경우 (메서드 형태만 서로 공유해서 재정의되는 상황일 때)
-
서로 관련성이 없는 클래스들이 인터페이스를 구현하게 되는 경우
-
특정 데이터 타입의 행동을 명시하고 싶은데 그 행동이 구현되는 위치를 신경쓰고 싶지 않은 경우
-
다중 상속을 허용하고 싶은 경우
참고
JAVA 8 이전과 이후의 가장 큰 차이는 인터페이스에서 메서드 구현부를 가질 수 있는지의 여부이다.
이전에는 인터페이스의 경우 메서드 구현부를 가질 수 없었지만 JAVA 8 이후에 인터페이스(default 키워드 사용)와 추상클래스 둘다 메서드 구현부를 가질 수 있게 되었다.