Home Java Interface - 객체 지향 프로그래밍의 관점에서
Post
Cancel

Java Interface - 객체 지향 프로그래밍의 관점에서

객체들의 소통 방식

객체 지향 프로그래밍에서 객체들은 어떻게 소통할까?
객체들은 각자 주어진 역할이 있고 그 역할을 수행하기 위한 책임을 갖는다. 객체들이 역할을 성실히 수행하면 하나의 커다란 애플리케이션을 완성할 수 있다.
객체들이 역할을 성실하게 수행하기 위해서는 자신들만의 명확한 역할과 책임을 가져야 한다. 따라서 다른 역할과 책임을 갖는 객체에 의존적이지 않아야 한다. 또한 객체들은 서로가 필요할 때 서로에게 요구사항을 전달할 수 있어야 한다.
요구사항을 전달하는 것은 여러 단어로 말할 수 있을 것 같다.

  • 요청
  • 소통
  • 협력

어떻게 서로 소통하는지에 대한 생각은 잠시 미뤄두고, 무엇을 소통할 수 있는지 생각해보자.

인터페이스란?

위키백과에는 인터페이스를 다음과 같이 설명한다.

인터페이스는 서로 다른 두 개의 시스템, 장치 사이에서 정보나 신호를 주고받는 경우의 접점이나 경계면이다.

우리는 다음과 같이 바꿔보자.

인터페이스는 서로 다른 두 객체 사이에서 요청을 주고받는 접점이다.

인터페이스는 두 객체 사이의 접점이다. (두! 객! 체!)

(예전에 서른명 정도 앞에서 인터페이스에 대해 발표할 일이 있었다. 그때는 Java를 처음 공부할 때여서 다음과 같이 말했다. ‘서로 관련이 없는 클래스라도 인터페이스에 정의된 기능을 구현하고 싶으면 사용한다.’ 뭔가 껍데기만 있는 느낌이다.)

Java에서 인터페이스는 추상 메서드를 갖는다. 위의 정의를 바탕으로 추상 메서드는 다음처럼 설명할 수 있을 것 같다.

추상 메서드는 해당 인터페이스를 구현한 객체에게 무엇을 요청할 수 있는지를 나타낸다.

인터페이스 I를 구현한 객체 A에게 인터페이스 I를 구현하지 않은 어떤 객체 B가 요청을 보내기 위해서는 인터페이스 I만 알면 된다. 심지어 객체 A에 대한 구현 클래스도 몰라도 된다. 객체 지향 프로그래밍 측면에서는 모를수록 좋을 것이다.

비유하자면 일종의 메뉴판 같은 것이다. 우리는 식당에 가서 메뉴판을 보고 주문을 한다. 일반적으로 메뉴판에는 요리 방법이 쓰여있지는 않다. 다만 우리는 메뉴판에 있는 음식 이름과 가격을 보고 주문한다.

1
2
3
4
5
6
public interface Menu {

    public abstract Pasta orderPasta(int price);
    public abstract Risotto orderRisotto(int price);
    public abstract Steak orderSteak(int price);
}

우리는 메뉴판을 보고 어떤 요청이 있고, 각각의 요청에는 어떤 것들이 필요하고, 무엇을 얻을 수 있는지 알 수 있다.

public일까?

위의 Menu에서 publicpublic abstract를 생략할 수 있다.
Java는 왜 생략 가능하게 만들었을까? 다르게 생각하면, Java는 왜 인터페이스에 public, public abstract를 자동으로 붙여줄까?
이렇게 함으로써 Java는 인터페이스를 public으로만 사용할 수 있고 public인 추상 메서드만 정의할 수 있게 강제한다.
만약 추상 메서드가 private인 경우를 생각해보자. 이런 경우 다른 객체는 해당 메서드를 호출할 수 없다. 이 말은 다른 객체와 소통할 때 사용할 수 없다는 뜻이다. 따라서 public이 아닌 메서드는 ‘어떻게’의 영역이라고 할 수 있다. private interface의 경우도 마찬가지이다.

1
2
3
4
5
6
private interface Menu {

    private abstract Pasta orderPasta(int price);
    private abstract Risotto orderRisotto(int price);
    private abstract Steak orderSteak(int price);
}

음식을 시킬 수도 없고, 심지어 음식점인지도 모를 것이다.

default method

default method는 조금 다른 이야기이다. Java 8부터 추가된 기능인데 인터페이스에 정의되는 메서드임에도 구현체가 있다. 간단하게만 설명해보겠다.

인터페이스를 구현한 클래스는 항상 모든 추상 메서드를 구현해야한다. 그렇지 않다면 다른 객체가 보기에는 이상할 것이다. 요청에 응답할 수도 없으면서 가능하다고 인터페이스에 명시해둔 셈이 된다.
이때 기존의 인터페이스에 새로운 추상 메서드를 추가하고 싶다면 어떤 문제가 발생할까? 정말 끔찍하게도 해당 인터페이스를 구현한 모든 클래스에 새로 추가된 추상 메서드를 새롭게 구현해야한다.
그래서 Java 개발자들은 기존의 구현을 고치지 않고도 인터페이스를 변경할 수 있는 방법을 고민했다. 그에 대한 결론은 default method인 것이다. default method는 구현하지 않아도 된다.

마치며

한달 전부터 정리해보고 싶은 글이었는데 드디어 작성한다!
Java를 처음 공부하면서 인터페이스를 접했을 때 많이 생소했다. Java는 왜 인터페이스라는 것을 제공하는지도 몰랐고 잘 이해가 가지 않았다.
그러나 OOP에 대해 공부를 하고 OOP를 잘 활용할 수 있게 도와주는 Spring을 공부하고 보니 비로소 조금씩 감을 잡는 것 같다. Java를 공부하면서 가장 재밌는 깨달음이었다. (두번째는 Enum)

This post is licensed under CC BY 4.0 by the author.