본문 바로가기

Programming/Javascript

13. Javascript 객체지향 프로그래밍(3) - 클래스 기반 상속 구현 3

 

앞의 아티클에서 만들어본 예제에 대해, 한 가지 약점이 더 남아있다는 말씀을 드렸습니다. 그럼 예제를 다시 한번 살펴보면서 어떤 점이 보완되어야 하는지 살펴보겠습니다.

 

function Rapper(arg){
    this.rapName = arg;
}

Rapper.prototype.setName = function(value) {
    this.rapName = value;
};

Rapper.prototype.getName = function() {
    return this.rapName;
};

function Smtm(arg){
    Rapper.apply(this, arguments);
}

var hype = new Rapper("SIMON D");
console.dir(hype);

Smtm.prototype = hype;

var youngKing = new Smtm("QM");
console.dir(youngKing);
// youngKing.setName("QM");
console.dir(youngKing);
console.log(youngKing.getName());

 

우선 위의 코드를 살펴보면, 기본적으로 '부모'와 '자식'객체의 기본 성질과 관련해 문제가 발생합니다. 만일 다른 OOP언어를 공부하신 분들이라면 쉽게 눈치채실 수도 있습니다. 바로, 자식 객체의 프로퍼티를 추가하는 과정에서의 문제점입니다. 아래의 구조도를 다시 한번 살펴볼까요?

 

 


 

'부모'객체와 '자식' 객체가 존재할 때, 기본적으로 자식 객체는 부모 객체를 상속하여 부모 객체의 프로퍼티와 메서드를 자신의 것처럼 사용할 수 있게 됩니다. 그러나 오직 '자식 객체'에만 추가되는 속성은 자식 객체에서만 사용할 수 있는 것이 일반적인 성질입니다. 

 

자, 이제부터는 앞의 내용을 잘 공부하셨다면 충분히 따라올 수 있는 내용들입니다. 객체 변수 youngKing을 비롯하여 생성자 함수 Smtm( )을 통해 생성된 객체들이 공통으로 쓸 수 있는 프로퍼티를 추가하기 위해서는 어떠한 과정을 거쳐야 할까요? 기본적으로 Smtm.prototype에 새로운 프로퍼티를 생성하게 됩니다. Smtm.prototype.xxx = ...; 형태가 되겠네요. 

 

그런데 여기서 하나 문제가 발생합니다. 생성자 함수 Smtm( )은 프로토타입을 별도로 생성해서 사용하지 않고, hype라는 객체를 대입시켜 사용하고 있는 상태입니다. 즉, Smtm( )은 자신의 부모 클래스인 Rapper( )의 인스턴스인 hype에 직접 접근하게 되는 것입니다. 이는 바람직한 구조라고 볼 수 없습니다. 즉, Smtm( )으로 생성된 youngKing에서 새로운 프로퍼티를 추가하고 싶을 경우에는, Rapper( )로 생성된 hype에는 아무 영향을 미쳐서는 안 되는 구조가 성립해야 합니다. 

 

 


 

이제, 아래와 같은 구조로 위의 Rapper와 Smtm의 구조를 재정립해 보겠습니다.

 

function Rapper(arg) {
    this.rapName = arg;
}

Function.prototype.method = function(name, func){
    this.prototype[name] = func;
};

Rapper.method("setName", function(value){
    this.rapName = value;
});

Rapper.method("getName", function(){
    return this.rapName;
});

// 여기까지 생성자 함수 Rapper() 정의

function Smtm(arg) {

}

function F() {};
F.prototype = Rapper.prototype;
// F()로 생성하게 되는 신규 객체는 Rapper.prototype을 [[Prototype]]으로 참조

Smtm.prototype = new F();
Smtm.prototype.constructor = Smtm;
Smtm.super = Rapper.prototype;

var youngKing = new Smtm();
youngKing.setName("THE QUIET");
console.log(youngKing.getName());
console.dir(youngKing);

 

다음 아티클에서 위 예제를 좀 더 자세히 살펴보겠습니다.