ABOUT ME

-

Today
-
Yesterday
-
Total
-
  • 객체지향에서 메세지와 메소드는 다르다.
    개발/OOP, Design Pattern 2021. 2. 24. 10:51

    객체지향에서 메세지와 메소드는 다르다.

    객체지향에 입문해서 자료를 보다보면 메세지 라는 말을 많이 보게 된다. 예를 들어 객체의 상태를 직접 변경하지 않고, 어떤 작업을 요청하는 메세지를 보내야 한다 라는 식이다.
    이렇게 보면 '아. 객체의 메소드를 사용해서 간접적으로 상태를 변경하라는 뜻이구나' 라는 생각이 든다. 그럼 왜 메소드를 쓰라고 하면 되지, 굳이 메세지를 보내라고 하는 걸까?

    메소드는 메세지를 수신하는 방법이다.

    다음과 같은 사람의 클래스가 있다고 가정하자.

    public abstract class Person {
        public abstract void sleep();
    }

    추상 클래스에 sleep() 이라는 추상 메소드가 정의되어 있고, 이것은 Person의 자식 클래스를 사용하는 사용자에게 sleep() 메소드를 사용할 수 있습니다. 라고 알려주는 인터페이스 역할을 하게 된다.

     

    다음은 구현체들이다.

    public class Baby extends Person {
        @Override
        public void sleep() {
            System.out.println("엄마 품에서 잔다.");
        }
    }
    
    public class Student extends Person {
        @Override
        public void sleep() {
            System.out.println("책상에 엎드려 잔다.");
        }
    }

    각각의 클래스에 sleep() 이라는 메소드가 정의되어 있다. 모두 Person의 sleep() 을 재정의했고 각각 다른 일을 수행한다. 각각의 클래스에 총 2개의 메소드가 존재한다. 여기까지는 모두 알고있는 이야기다.

     

    이때, 이 클래스를 사용하는 코드도 작성해보자.

    public class Main {
        public static void main(String[] args) {
            Person student = new Student();        
            student.sleep();
        }
    }

    코드를 작성하는 우리 입장에서는 'student는 Person을 상속받은 Student 클래스가 할당되어 있군.' 이라고 한눈에 알 수 있지만,
    컴파일러의 입장에서는 Person 타입으로 업캐스팅되어 컴파일 시점에는 어떤 클래스의 sleep() 을 실행해야 하는지 알 수 없다.
    런타임 시점이 되어서야 Student 클래스의 sleep() 을 실행하기로 결정한다. (이것을 다형성 이라고 한다.)

     

    흐름을 정리하자면

    • student 객체에게 sleep() 이라는 메세지를 전달한 것이고
    • student 객체의 타입인 Person 클래스는 sleep() 이라는 추상메소드를 가지고 있으므로 메세지를 수신할 수 있고
    • 수신된 메세지는 런타임에 자식클래스인 Student 클래스의 sleep() 이 호출되는 것이다.

    만약 student.wakeUp() 이라는 메세지를 전달하면 어떻게 될까?
    당연히 Person 클래스에는 wakeUp() 이라는 인터페이스가 정의되어 있지 않으므로 메세지를 수신할 수 없고 컴파일러는 에러를 뱉는다.

    간략한 결론

    클래스를 사용하는 측에서 객체를 이용해서 코드를 호출하려는 행위를 '메세지를 보낸다' 라고 할 수 있고,
    그 메세지를 수신할 방법을 정의해놓은 것이 '메소드' 라고 할 수 있겠다.

     

     

    참고

    조영호님 - 오브젝트

    댓글

Designed by Tistory.