일 | 월 | 화 | 수 | 목 | 금 | 토 |
---|---|---|---|---|---|---|
1 | 2 | 3 | ||||
4 | 5 | 6 | 7 | 8 | 9 | 10 |
11 | 12 | 13 | 14 | 15 | 16 | 17 |
18 | 19 | 20 | 21 | 22 | 23 | 24 |
25 | 26 | 27 | 28 | 29 | 30 | 31 |
- 자바
- 매개변수참조
- 인스턴스메소드
- 선택한요소
- 구현클래스
- 인터페이스의역할
- 상속
- 배열을 문자열
- jQuery
- ZipInputStream
- createTempFile
- 필드의다형성
- 문자열을 배열
- 자동타입변환
- 상수필드
- 요소
- 생성자참조
- 공백 처리
- find
- 추상메소드
- 정적메소드
- 객체타입확인
- 람다식
- 타깃타입
- java
- map에서key와value
- 디폴트메소드
- 인터페이스
- 익명구현객체
- 오버라이딩
- Today
- Total
코드지우개
인터페이스 ② 본문

개발 코드가 인터페이스 메소드를 호출하면 인터페이스는 객체의 메소드를 호출한다.
객체는 인터페이스에서 정의된 추상 메소드와 동일한 메소드 이름, 매개 타입, 리턴 타입을 가진 실체 메소드를 가지고 있어야 한다.
이러한 객체를 인터페이스의 구현( implement ) 객체라고 하고, 구현 객체를 생성하는 클래스를 구현 클래스라고 한다.
구현 클래스
public class 구현클래스명 implements 인터페이스명 {
인터페이스에 선언된 추상 메서드의 실체 메소드 선언
}
구현 클래스는 보통의 클래스와 동일한데, 인터페이스 타입으로 사용할 수 있음을 알려주기 위해 클래스 선언부에 implements 키워드를 추가하고 인터페이스명을 명시해야 한다.
그리고 인터페이스에 선언된 추상 메소드의 실체 메소드를 선언해야 한다.
RemoteControl 인터페이스
public interface RemoteControl {
//상수
int MAX_VOLUME = 10;
int MIN_VOLUME = 0;
//추상 메소드
void turnOn();
void turnOff();
void setVolume( int volume );
//디폴트 메소드
default void setMute( boolean mute ){
if( mute ){
System.out.println( "무음 처리합니다." );
}else{
System.out.println( "무음 해제합니다." );
}
}
//정적 메소드
static void changeBattery(){
System.out.println( "건전지를 교환합니다." );
}
}
추상 메소드의 실체메소드를 작성하는 방법
- 메소드의 선언 부가 정확히 일치해야 한다.
- 인터페이스의 모든 추상메서드를 재정의하는 실체 메소드를 작성해야 한다.
ex) 5개 추상 메소드 -> 5개 오버라이딩 - 일부만 재정의할 경우, 추상 클래스로 선언해야 하며 abstract 키워드를 붙여야 한다.
public abstract class Television implements RemoteControl{
public void turnOn(){...} setVolume() 실체 메소드가없다.
public void turnOff(){...} (일부만 구현)
}
Television 구현 클래스
public class Television implements RemoteControl{
//필드
private int volume;
//turnOn() 추상 메소드의 실체 메소드
@Override
public void turnOn() {
System.out.println( "TV를 켭니다." );
}
//turnOff() 추상 메소드의 실체 메소드
@Override
public void turnOff() {
System.out.println( "TV를 끕니다." );
}
//setVolume() 추상 메소드의 실체 메소드 (인터페이스 상수를 이용해서 volume 필드의 값 제한)
@Override
public void setVolume(int volume) {
if( volume > RemoteControl.MAX_VOLUME ){ //매개값이 Max 보다 클경우 필드값 Max값으로
this.volume = RemoteControl.MAX_VOLUME;
}else if( volume < RemoteControl.MIN_VOLUME ){ //매개값이 Min 보다 작을경우 필드값 Min값으로
this.volume = RemoteControl.MIN_VOLUME;
}else{
this.volume = volume;
}
System.out.println( "현재 TV 볼륨 : " + this.volume );
}
}
Audio 구현 클래스
public class Audio implements RemoteControl{
//필드
private int volume;
//turnOn() 추상 메소드의 실체 메소드
@Override
public void turnOn() {
System.out.println( "Audio를 켭니다." );
}
//turnOff() 추상 메소드의 실체 메소드
@Override
public void turnOff() {
System.out.println( "Audio를 끕니다." );
}
//setVolume() 추상 메소드의 실체 메소드 (인터페이스 상수를 이용해서 volume 필드의 값 제한)
@Override
public void setVolume(int volume) {
if( volume > RemoteControl.MAX_VOLUME ){ //매개값이 Max 보다 클경우 필드값 Max값으로
this.volume = RemoteControl.MAX_VOLUME;
}else if( volume < RemoteControl.MIN_VOLUME ){ //매개값이 Min 보다 작을경우 필드값 Min값으로
this.volume = RemoteControl.MIN_VOLUME;
}else{
this.volume = volume;
}
System.out.println( "현재 Audio 볼륨 : " + this.volume );
}
}
구현 클래스에서 인터페이스의 추상 메소드들에 대한 실체 메소드를 작성할 때 주의할 점은 인터페이스의 모든 메소드는 기본적으로 public 접근 제한을 갖기 때문에 public 보다 더 낮은 접근 제한으로 작성할 수 없다.
RemoteControlExample 실행 클래스
public class RemoteControlExample {
public static void main(String[] args){
RemoteControl remote; //인터페이스 변수
remote = new Television(); //RemoteControl인터페이스를 구현한 구현클래스만 가능
remote.turnOn(); //출력 : TV를 켭니다.
remote.turnOff(); //출력 : TV를 끕니다.
remote = new Audio(); //RemoteControl인터페이스를 구현한 구현클래스만 가능
remote.turnOn(); //출력 : Audio를 켭니다.
remote.turnOff(); //출력 : Audio를 끕니다.
}
}
인터페이스로 구현 객체를 사용하려면 인터페이스 변수를 선언하고 구현 객체를 대입해야 한다.
인터페이스 변수는 참조 타입이기 때문에 구현 객체가 대입될 경우 구현 객체의 번지를 저장한다.
익명 구현 객체
익명 구현 객체는 말 그대로 이름이 없는 구현 객체이다.
구현 클래스를 만들어 사용하는 것이 일반적이고, 클래스를 재사용할 수 있기 때문에 편리하지만,
일회성의 구현 객체를 만들기 위해 소스 파일을 만들고 클래스를 선언하는 것은 비효율적이다.
자바는 소스 파일을 만들지 않고도 구현 객체를 만들 수 있는 방법을 제공하는데, 그것이 익명 구현 객체이다.
인터페이스 변수 = new 인터페이스(){
//인터페이스에 선언된 추상 메소드의 실체 메소드 선언
};
new 연산자 뒤에는 클래스 이름이 와야 하는데, 이름이 없다. 인터페이스(){}는 인터페이스를 구현해서 중괄호{}와 같이 클래스를 선언하라는 뜻이고, new 연산자는 이렇게 선언된 클래스를 객체로 생성한다.
중괄호{}에는 인터페이스에 선언된 모든 추상 메소드들의 실체 메소드를 작성해야 한다. 그렇지 않으면 컴파일 에러가 발생한다.
추가적으로 필드와 메소드를 선언할 수 있지만, 익명 객체 안에서만 사용할 수 있고 인터페이스 변수로 접근할 수 없다.
작성 시 주의할 점은 하나의 실행문이므로 끝에는 세미콜론( ; )을 반드시 붙여야 한다.
public class RemoteControlExample {
public static void main(String[] args) {
RemoteControl remote = new RemoteControl() {
@Override
public void turnOn() {
System.out.println("turnOn 실행~~");
}
@Override
public void turnOff() {
System.out.println("turnOff 실행~~");
}
@Override
public void setVolume(int volume) {
System.out.println("setVolume 실행 volume = " + volume);
testMethod();
}
public void testMethod(){
System.out.println("testMethod 실행~~");
}
};
remote.turnOn(); //출력 : turnOn 실행~~
remote.turnOff(); //출력 : turnOff 실행~~
remote.setVolume(10); //출력 setVolume 실행 volume = 10 / testMethod 실행~~
//remote.testMethod(); 호출 불가능
}
}
모든 구현 객체는 클래스로부터 생성되는데, 익명 구현 객체도 예외는 아니다. RemoteControlExample.java를 컴파일하면 자바 컴파일러에 의해 자동으로 클래스 파일이 만들어진다.
RemoteControlExample$1.class
RemoteControlExample 이름 뒤에 $가 붙고 생성 번호가 붙는데 생성 번호는 1번부터 시작한다.
만약 두 번째 익명 구현 객체를 만들었다면 클래스 파일명은 RemoteControlExample$2.class가 된다.