JavaScript 계승 의 특성 과 실천 응용 에 대한 심도 있 는 설명

11628 단어
본 고 는 자 바스 크 립 트 계승의 특성 과 실천 응용 을 상세 하 게 서술 하 였 다.여러분 께 참고 하도록 공유 하 겠 습 니 다. 구체 적 으로 는 다음 과 같 습 니 다.
계승 은 코드 재 활용 모델 입 니 다.JavaScript 는 클래스 기반 모드 를 모 의 할 수 있 으 며, 다른 표 현 력 있 는 모드 도 지원 합 니 다.하지만 간단 함 을 유지 하 는 것 이 최선 이다.
자 바스 크 립 트 는 원형 을 바탕 으로 하 는 언어 로 다른 대상 을 직접 계승 할 수 있다 는 것 이다.
위류
JavaScript 의 원형 은 대상 을 다른 대상 에서 직접 계승 하 는 것 이 아니 라 불필요 한 간접 층 을 삽입 합 니 다. 구조 함 수 를 통 해 대상 을 만 듭 니 다.
함수 가 생 성 될 때 Function 구조 기 에서 생 성 된 함수 대상 은 이러한 유사 한 코드 를 실행 합 니 다.

this.prototype = {constructor : this};


새로운 함수 대상 에 prototype 속성 이 추가 되 었 습 니 다. constructor 속성 을 포함 하고 속성 값 이 새 함수 인 대상 입 니 다.
구조 기 호출 모드, 즉 new 로 함 수 를 호출 할 때 이렇게 실 행 됩 니 다.

Function.method('new', function (){
  var that = Object.create(this.prototype);//                     
  var other = this.apply(that, arguments);//       ,   this     
  return (typeof other === 'object' && other) || that;//               ,          
});


우 리 는 구조 기 를 정의 한 후에 그것 의 원형 을 확대 할 수 있다.

//          
var Mammal = function (name) {
  this.name = name;
};
Mammal.prototype.get_name = function () {
  return this.name;
};
Mammal.prototype.says = function () {
  return this.saying || '';
};


그리고 인 스 턴 스 구성:

var myMammal = new Mammal('Herb the mammal');
console.log(myMammal.get_name());//Herb the mammal


Mammal 을 계승 하기 위해 다른 위 류 를 만 듭 니 다 (구조 기 함 수 를 정의 하고 prototype 을 교체 합 니 다).

var Cat = function (name) {
  this.name = name;
  this.saying = 'meow';
};
Cat.prototype = new Mammal();


확장 원형:

Cat.prototype.purr = function (n) {
  var i, s = '';
  for (i = 0; i < n; i += 1) {
    if (s) {
      s += '-';
    }
    s += 'r';
  }
  return s;
};
Cat.prototype.get_name = function () {
  return this.says() + ' ' + this.name + ' ' + this.says();
};
var myCat = new Cat('Henrietta');
console.log(myCat.says());//meow
console.log(myCat.purr(5));//r-r-r-r-r
console.log(myCat.get_name());//meow Henrietta meow


우 리 는 method 방법 을 사용 하여 inherits 방법 을 정의 하여 이 추악 한 세부 사항 을 숨 깁 니 다.

/**
 *   Function.prototype    method   
 * @param name     
 * @param func   
 * @returns {Function}
 */
Function.prototype.method = function (name, func) {
  if (!this.prototype[name])//      ,   
    this.prototype[name] = func;
  return this;
};
Function.method('inherits', function (Parent) {
  this.prototype = new Parent();
  return this;
});


이 두 가지 방법 은 모두 this 로 돌아 갑 니 다. 그러면 우 리 는 직렬 연결 방식 으로 프로 그래 밍 할 수 있 습 니 다. O (∩ ∩) O ~

var Cat = function (name) {
  this.name = name;
  this.saying = 'meow';
}.inherits(Mammal).method('purr', function (n) {
    var i, s = '';
    for (i = 0; i < n; i += 1) {
      if (s) {
        s += '-';
      }
      s += 'r';
    }
    return s;
  }).method('get_name', function () {
    return this.says() + ' ' + this.name + ' ' + this.says();
  });
var myCat = new Cat('Henrietta');
console.log(myCat.says());//meow
console.log(myCat.purr(5));//r-r-r-r-r
console.log(myCat.get_name());//meow Henrietta meow


비록 우 리 는 '클래스' 와 같은 구조 기 함수 가 있 지만 개인 환경 이 없고 모든 속성 이 공개 적 이 며 부모 클래스 에 접근 할 수 없 는 방법 이 있 습 니 다.
구조 함 수 를 호출 할 때 new 접 두 사 를 추가 하 는 것 을 잊 어 버 리 면 this 는 새로운 대상 에 연결 되 지 않 고 전역 변수 에 연결 되 어 있 습 니 다!!이렇게 해서 우 리 는 새로운 대상 을 확충 하지 않 았 을 뿐만 아니 라 전체적인 변수 환경 도 파괴 했다.
이것 은 심각 한 언어 설계 오류 다!이 문제 가 발생 할 확률 을 낮 추기 위해 모든 구조 기 함 수 는 이니셜 대문자 로 명명 하기 로 약속 했다.이렇게 우 리 는 이니셜 대문자 형식의 함 수 를 보면 구조 기 함수 임 을 알 수 있 습 니 다. O (∩ ∩) O ~
물론 더 좋 은 전략 은 구조 기 함 수 를 전혀 사용 하지 않 는 것 이다.
2 대상 설명자
때때로 구조 기 는 많은 파 라 메 터 를 받 아들 여야 하기 때문에 매우 번거롭다.따라서 구조 기 를 작성 할 때 간단 한 대상 설명 자 를 받 아들 이 는 것 이 좋 습 니 다.

var myObject = maker({
 first: f,
 middle: m,
 last: l
});


현재 이 매개 변 수 는 임의의 순서에 따라 배열 할 수 있 습 니 다. 또한 구조 기 는 들 어 오지 않 은 매개 변 수 를 위해 기본 값 을 똑똑 하 게 사용 할 수 있 습 니 다. 코드 도 쉽게 읽 을 수 있 습 니 다. O (∩ ∩) O ~
3 원형
원형 을 바탕 으로 하 는 계승 이란 새로운 대상 이 오래된 대상 의 속성 을 계승 할 수 있다 는 것 을 말한다.먼저 유용 한 대상 을 만 든 다음 에 그 대상 과 유사 한 대상 을 더 많이 만 들 수 있다.

/**
 *   
 */
var myMammal = {
  name: 'Herb the mammal',
  get_name: function () {
    return this.name;
  },
  says: function () {
    return this.saying || '';
  }
};
//     
var myCat = Object.create(myMammal);
myCat.name = 'Henrietta';
myCat.saying = 'meow';
myCat.purr = function (n) {
  var i, s = '';
  for (i = 0; i < n; i += 1) {
    if (s) {
      s += '-';
    }
    s += 'r';
  }
  return s;
};
myCat.get_name = function () {
  return this.says() + ' ' + this.name + ' ' + this.says();
};
console.log(myCat.says());//meow
console.log(myCat.purr(5));//r-r-r-r-r
console.log(myCat.get_name());//meow Henrietta meow


create 방법 으로 새로운 인 스 턴 스 를 만 듭 니 다:

Object.create = function (o) {
    var F = function () {
    };
    F.prototype = o;
    return new F();
 }


4 함수 화
지금까지 본 계승 모델 의 문 제 는 프라이버시 를 보호 할 수 없고 대상 의 모든 속성 을 볼 수 있다 는 것 이다.일부 무식 한 프로그래머 들 은 개인 적 인 것 으로 위장 하 는 모델 을 사용한다. 즉, 개인 적 인 속성 이 필요 한 이상 한 이름 을 짓 고 코드 를 사용 하 는 다른 프로그래머 들 이 보이 지 않 는 척 하 기 를 바란다!
사실 더 좋 은 방법 이 있 습 니 다. 모듈 모드 를 응용 합 니 다.
우 리 는 먼저 대상 을 만 드 는 함 수 를 만 듭 니 다. 이 절 차 는 ①. 새로운 대상 을 만 듭 니 다.이것 은 네 가지 방식 이 있다.[2] 구조 기 함 수 를 호출 합 니 다.[3] 존재 하 는 대상 의 새로운 인 스 턴 스 를 구성 합 니 다.【 4 】 대상 에 게 돌아 갈 수 있 는 함 수 를 호출 합 니 다.②. 개인 인 스 턴 스 변수 와 방법 을 정의 합 니 다.③. 이 새로운 대상 을 확장 하 는 방법 은 이러한 매개 변수 에 접근 할 수 있 는 특권 을 가진다.④. 이 새로운 대상 으로 돌아간다.
함수 화 구조 기의 위조 코드 는 다음 과 같다.

var constructor = function (spec, my){
  var that,       ;
  my = my || {};
 //             my  
 that =      
 //    that      
 return that;
};


spec 대상 은 새로운 인 스 턴 스 를 구성 해 야 하 는 모든 정 보 를 포함 하고 있 으 며, 개인 변수 나 다른 함수 에 사용 할 수 있 습 니 다.my 대상 은 하나의 계승 체인 에 있 는 구조 기 에 공 유 된 용 기 를 제공 합 니 다. 들 어 오지 않 으 면 my 대상 을 만 듭 니 다.
특권 을 만 드 는 방법 은 함 수 를 개인 적 인 방법 으로 정의 한 다음 that 에 배분 하 는 것 입 니 다.

var methodical = function (){
 ...
};
that.methodical = methodical;


이렇게 두 단계 로 나 누 어 정의 하 는 장점 은 개인 적 인 methodical 이 이 인 스 턴 스 의 영향 을 받 지 않 는 다 는 것 이다.
현재, 우 리 는 이 모드 를 mammal 예제 에 적용 합 니 다.

var mammal = function (spec) {
  var that = {};
  that.get_name = function () {
    return spec.name;
  };
  that.says = function () {
    return spec.saying || '';
  };
  return that;
};
var myMammal = mammal({name: 'Herb'});
console.log(myMammal.get_name());//Herb
var cat = function (spec) {
  spec.saying = spec.saying || 'meow';
  var that = mammal(spec);
  that.purr = function (n) {
    var i, s = '';
    for (i = 0; i < n; i += 1) {
      if (s) {
        s += '-';
      }
      s += 'r';
    }
    return s;
  };
  that.get_name = function () {
    return that.says() + ' ' + spec.name + ' ' + that.says();
  };
  return that;
};
var myCat = cat({name: 'Henrietta'});
console.log(myCat.says());//meow
console.log(myCat.purr(5));//r-r-r-r-r
console.log(myCat.get_name());//meow Henrietta meow


함수 화 모드 는 부모 클래스 의 방법 도 호출 할 수 있다.여기 서 우 리 는 슈퍼 주 니 어 방법 을 구성 합 니 다. 그것 은 어떤 방법 이름 을 호출 하 는 함 수 를 되 돌려 줍 니 다.

//            
Object.method('superior', function (name) {
  var that = this,
    method = that[name];
  return function () {
    return method.apply(that, arguments);
  };
});


현재 coolcat 를 만 듭 니 다. 부모 클래스 를 호출 할 수 있 는 get 을 가지 고 있 습 니 다.name:

var coolcat = function (spec) {
  var that = cat(spec),
    super_get_name = that.superior('get_name');
  that.get_name = function (n) {
    return 'like ' + super_get_name() + ' baby';
  };
  return that;
};
var myCoolCat = coolcat({name: 'Bix'});
console.log(myCoolCat.get_name());//like meow Bix meow baby


함수 화 모델 은 매우 유연성 이 있 고 포장, 정보 감 춤 과 부모 유형 을 방문 하 는 방법 을 잘 실현 할 수 있다.
대상 의 모든 상태 가 사유 라면 위조 방지 대상 이 라 고 한다.이 대상 의 속성 은 교체 되 거나 삭 제 될 수 있 지만 이 대상 의 상 태 는 영향 을 받 지 않 습 니 다.함수 화 모드 로 대상 을 만 들 고 이 대상 의 모든 방법 이 this 나 that 를 사용 하지 않 는 다 면 이 대상 은 영구적 이 며 침입 되 지 않 습 니 다.특권 적 인 방법 이 존재 하지 않 는 한 이 영구적 인 대상 의 내부 상태 에 접근 할 수 없습니다.
5 이벤트 처리 함수
모든 대상 에 게 간단 한 이벤트 처리 기능 을 추가 할 수 있 는 함 수 를 만 들 수 있 습 니 다.여기 서 우 리 는 이 대상 에 on 방법, fire 방법 과 개인 적 인 이벤트 등록 대상 을 추가 합 니 다.

var eventuality = function (that) {
  var registry = {};
  /**
   *     
   *
   *    'on'                
   * @param              ,        type   (      )   。
   */
  that.fire = function (event) {
    var array,
      func,
      handler,
      i,
      type = typeof event === 'string' ? event : event.type;
    //          ,        
    if (registry.hasOwnProperty(type)) {
      array = registry[type];
      for (i = 0; i < array.length; i += 1) {
        handler = array[i];//                  
        func = handler.method;
        if (typeof func === 'string') {//             ,    
          func = this[func];
        }
        //   。          ,     ,         
        func.apply(this, handler.parameters || [event]);
      }
    }
    return this;
  };
  /**
   *       
   * @param type
   * @param method
   * @param parameters
   */
  that.on = function (type, method, parameters) {
    var handler = {
      method: method,
      parameters: parameters
    };
    if (registry.hasOwnProperty(type)) {//     ,      
      registry[type].push(handler);
    } else {//  
      registry[type] = [handler];
    }
    return this;
  };
  return that;
};


모든 단독 대상 에서 이벤트 처리 방법 을 부여 할 수 있 습 니 다.that 가 되 돌아 오기 전에 구조 함수 에서 호출 할 수도 있 습 니 다.

eventuality(that);


JavaScript 약 한 유형의 특성 은 여기 서 큰 장점 입 니 다. 왜냐하면 우 리 는 대상 계승 관계 의 유형 O (∩ ∩) O 를 처리 할 필요 가 없 기 때 문 입 니 다.
관심 있 는 친 구 는 본 사이트 의 온라인 HTML / CSS / JavaScript 코드 실행 도 구 를 사용 할 수 있 습 니 다.http://tools.jb51.net/code/HtmlJsRun상기 코드 운행 결 과 를 테스트 합 니 다.
더 많은 자 바스 크 립 트 관련 내용 은 본 사이트 의 주 제 를 볼 수 있 습 니 다.,,,,,,,,,,,,
본 고 에서 말 한 것 이 여러분 의 자 바스 크 립 트 프로 그래 밍 에 도움 이 되 기 를 바 랍 니 다.

좋은 웹페이지 즐겨찾기