JS 일부 특수 지식 점 (7) - 구조 함수 및 대상 지향 모델
44809 단어 Web앞 머리 를 푹 삶다
new 명령 의 원리
new
명령 을 사용 할 때 그 뒤의 함 수 는 다음 절 차 를 순서대로 실행 합 니 다.돌아 올 대상 의 인 스 턴 스 로 빈 대상 을 만 듭 니 다.
이 빈 대상 의 원형 을 구조 함수
prototype
속성 을 가리킨다. 이 빈 대상 을 함수 내부 의
this
키워드 에 할당 합 니 다. 구조 함수 내부 코드 를 실행 하기 시작 합 니 다.
new.target
함수 내부 에서
new.target
속성 을 사용 할 수 있 습 니 다.현재 함수 가 new
명령 호출 이 라면 new.target
현재 함 수 를 가리 키 고 그렇지 않 으 면 undefined
입 니 다.function f() {
console.log(new.target === f);
}
f() // false
new f() // true
이 속성 을 사용 하면 함수 호출 시
new
명령 을 사용 할 지 여 부 를 판단 할 수 있 습 니 다.function f() {
if (!new.target) {
throw new Error(' new !');
}
// ...
}
f() // Uncaught Error: new !
이 절 은 자 바스 크 립 트 언어의 실제 프로 그래 밍 에서 대상 을 대상 으로 프로 그래 밍 하 는 일부 모델 을 소개 한다.
구조 함수 의 계승
하나의 구조 함수 로 하여 금 다른 구조 함 수 를 계승 하 게 하 는 것 은 매우 흔히 볼 수 있 는 수요 이다.
이것 은 두 단계 로 나 누 어 실현 할 수 있다.첫 번 째 단 계 는 하위 클래스 의 구조 함수 에서 부모 클래스 의 구조 함 수 를 호출 하 는 것 이다.
function Sub(value) {
Super.call(this);
this.prop = value;
}
위의 코드 에서
Sub
는 하위 클래스 의 구조 함수 이 고 this
는 하위 클래스 의 인 스 턴 스 입 니 다.인 스 턴 스 에서 부모 클래스 의 구조 함수 Super
를 호출 하면 하위 클래스 인 스 턴 스 가 부모 클래스 인 스 턴 스 의 속성 을 가지 게 됩 니 다.두 번 째 단 계 는 자 류 의 원형 이 아버지 류 의 원형 을 가리 키 게 하 는 것 이다. 이런 유형 은 아버지 류 의 원형 을 계승 할 수 있다.
Sub.prototype = Object.create(Super.prototype);
Sub.prototype.constructor = Sub;
Sub.prototype.method = '...';
위의 코드 에서
Sub.prototype
는 하위 클래스 의 원형 으로 직접 Object.create(Super.prototype)
가 아니 라 Super.prototype
로 할당 해 야 합 니 다.그렇지 않 으 면 뒤의 두 줄 Sub.prototype
에 대한 조작 은 아버지 류 의 원형 Super.prototype
과 함께 수정 된다.또 다른 문법 은
Sub.prototype
부계 실례 와 같다.Sub.prototype = new Super();
위의 이런 문법 도 계승 하 는 효과 가 있 지만 자 류 는 부류 의 실례 를 가 진 방법 이 있다.때때로 이것 은 우리 가 필요 로 하 는 것 이 아 닐 수도 있 기 때문에 이런 문법 을 사용 하 는 것 을 추천 하지 않 는 다.
예 를 들 어 다음은 구조 함수 이다.
function Shape() {
this.x = 0;
this.y = 0;
}
Shape.prototype.move = function (x, y) {
this.x += x;
this.y += y;
console.info('Shape moved.');
};
우 리 는
Shape
구조 함수 계승 Rectangle
을 필요 로 한다.// ,
function Rectangle() {
Shape.call(this); //
}
//
function Rectangle() {
this.base = Shape;
this.base();
}
// ,
Rectangle.prototype = Object.create(Shape.prototype);
Rectangle.prototype.constructor = Rectangle;
이러한 서법 을 사용 한 후에
Shape
연산 자 는 하위 클래스 와 부모 클래스 의 구조 함수 에 대해 모두 되 돌려 줍 니 다 instanceof
.var rect = new Rectangle();
rect.move(1, 1) // 'Shape moved.'
rect instanceof Rectangle // true
rect instanceof Shape // true
위의 코드 에서 자 류 는 전체 계승 부류 이다.때로는 하나의 방법의 계승 만 필요 할 때 아래 의 서법 을 채택 할 수 있다.
ClassB.prototype.print = function() {
ClassA.prototype.print.call(this);
// some code
}
위의 코드 에서 하위 클래스
true
의 B
방법 은 먼저 부모 클래스 print
의 A
방법 을 호출 한 다음 에 자신의 코드 를 배치 합 니 다.부계 print
의 A
방법 을 물 려 받 은 셈 이다.다 중 상속
자 바스 크 립 트 는 한 대상 이 여러 대상 을 동시에 계승 할 수 없 도록 다 중 계승 기능 을 제공 하지 않 습 니 다.하지만 변 칙 적 인 방법 을 통 해 이 기능 을 실현 할 수 있다.
function M1() {
this.hello = 'hello';
}
function M2() {
this.world = 'world';
}
function S() {
M1.call(this);
M2.call(this);
}
// M1
S.prototype = Object.create(M1.prototype);
// M2
Object.assign(S.prototype, M2.prototype);
//
S.prototype.constructor = S;
var s = new S();
s.hello // 'hello:'
s.world // 'world'
상기 코드 에서 하위 클래스
print
는 부모 클래스 S
와 M1
를 동시에 계승 했다.이런 모델 을 Mixin (혼합) 이 라 고도 부른다.모듈
사이트 가 점차 '인터넷 응용 프로그램' 으로 변 함 에 따라 웹 페이지 에 삽 입 된 자 바스 크 립 트 코드 는 갈수 록 방대 해 지고 복잡 해진 다.웹 페이지 는 점점 데스크 톱 프로그램 과 같 아 지고 있 습 니 다. 팀 분업 협력, 진도 관리, 유닛 테스트 등 이 필요 합 니 다. 개발 자 는 소프트웨어 공학 의 방법 을 사용 하여 웹 페이지 의 업무 논 리 를 관리 해 야 합 니 다.
JavaScript 모듈 화 프로 그래 밍 은 이미 절실 한 수요 가 되 었 다.이상 적 인 상황 에서 개발 자 는 핵심 적 인 업무 논리 만 실현 하고 다른 사람들 이 이미 작성 한 모듈 을 불 러 올 수 있 습 니 다.
그러나 자 바스 크 립 트 는 모듈 화 프로 그래 밍 언어 가 아니 라 ES5 는 '클래스' (class) 를 지원 하지 않 으 며 '모듈' (module) 을 논 할 필요 가 없다.ES6 는 '클래스' 와 '모듈' 을 공식 적 으로 지원 하지만 아직 주류 가 되 지 는 않 았 다.자 바스 크 립 트 커 뮤 니 티 는 기 존의 운영 환경 에서 모듈 의 효 과 를 실현 하기 위해 많은 노력 을 기 울 였 다.
기본 적 실현 방법
모듈 은 특정 기능 을 실현 하 는 속성 과 방법의 패키지 이다.
서로 다른 함수 (그리고 상 태 를 기록 하 는 변수) 를 간단하게 함께 놓 으 면 하나의 모듈 이 라 고 할 수 있다.
function m1() {
//...
}
function m2() {
//...
}
위의 함수 m1 () 과 m2 () 는 하나의 모듈 을 구성한다.사용 할 때 직접 호출 하면 됩 니 다.
이런 방법의 단점 은 매우 뚜렷 하 다. '전체 변 수 를 오염 시 켰 기 때문에 다른 모듈 과 변수 명 충돌 이 발생 하지 않 고 모듈 구성원 간 에 직접적인 관 계 를 볼 수 없다.
위의 단점 을 해결 하기 위해 모듈 을 하나의 대상 으로 쓸 수 있 고 모든 모듈 구성원 이 이 대상 에 넣 을 수 있다.
var module1 = new Object({
_count : 0,
m1 : function (){
//...
},
m2 : function (){
//...
}
});
위의 함수
M2
와 m1
는 모두 m2
대상 에 밀봉 되 어 있다.사용 할 때 이 대상 의 속성 을 호출 합 니 다.module1.m1();
그러나 이런 표기 법 은 모든 모듈 구성원 을 폭로 하고 내부 상 태 는 외부 에서 고 칠 수 있다.예 를 들 어 외부 코드 는 내부 카운터 의 값 을 직접 바 꿀 수 있다.
module1._count = 5;
패키지 개인 변수: 구조 함수 의 쓰기
우 리 는 구조 함 수 를 이용 하여 사유 변 수 를 봉인 할 수 있다.
function StringBuilder() {
var buffer = [];
this.add = function (str) {
buffer.push(str);
};
this.toString = function () {
return buffer.join('');
};
}
이런 방법 은 사유 변 수 를 구조 함수 에 봉 하여 구조 함수 와 실례 대상 이 분리 되 는 원칙 을 위반 했다.그리고 메모 리 를 많이 쓴다.
function StringBuilder() {
this._buffer = [];
}
StringBuilder.prototype = {
constructor: StringBuilder,
add: function (str) {
this._buffer.push(str);
},
toString: function () {
return this._buffer.join('');
}
};
이러한 방법 은 개인 변 수 를 인 스 턴 스 대상 에 넣 으 면 더욱 자 연 스 러 워 보이 지만 개인 변 수 는 외부 에서 읽 고 쓸 수 있어 안전 하지 않다.
패키지 개인 변수: 함수 쓰기 즉시 실행
"즉시 실행 함수" (Immediately - Invoked Function Expression, IIFE) 를 사용 하여 관련 속성 과 방법 을 함수 역할 영역 에 밀봉 하면 개인 구성원 이 노출 되 지 않 는 목적 을 달성 할 수 있 습 니 다.
var module1 = (function () {
var _count = 0;
var m1 = function () {
//...
};
var m2 = function () {
//...
};
return {
m1 : m1,
m2 : m2
};
})();
위의 쓰기 방법 을 사용 하면 외부 코드 는 내부 의
module1
변 수 를 읽 을 수 없습니다.console.info(module1._count); //undefined
위의
_count
는 자바 스 크 립 트 모듈 의 기본 적 인 쓰기 입 니 다.다음은 이런 표기 법 을 가공 하 겠 습 니 다.모듈 의 증폭 모드
만약 에 하나의 모듈 이 매우 크다 면 반드시 몇 부분 으로 나 누 어야 하거나 하나의 모듈 이 다른 모듈 을 계승 해 야 한다. 이때 '확대 모드' (augmentation) 를 사용 할 필요 가 있다.
var module1 = (function (mod){
mod.m3 = function () {
//...
};
return mod;
})(module1);
위의 코드 는
module1
모듈 에 새로운 방법 module1
을 추가 한 다음 에 새로운 m3()
모듈 로 돌아 갑 니 다.브 라 우 저 환경 에서 모듈 의 각 부분 은 보통 인터넷 에서 가 져 오 는데 어떤 부분 이 먼저 불 러 올 지 알 수 없습니다.위의 쓰기 방법 을 사용 하면 첫 번 째 로 실 행 된 부분 에 빈 대상 이 없 는 것 을 불 러 올 수 있 습 니 다. 이 때 는 '넓 은 확대 모드' (Loose augmentation) 를 사용 해 야 합 니 다.
var module1 = ( function (mod){
//...
return mod;
})(window.module1 || {});
'확대 모드' 에 비해 '넓 은 확대 모드' 는 '즉시 실행 함수' 의 매개 변 수 는 빈 대상 일 수 있 습 니 다.
전역 변수 입력
독립 성 은 모듈 의 중요 한 특징 으로 모듈 내 부 는 프로그램의 다른 부분 과 직접 상호작용 하지 않 는 것 이 가장 좋다.
모듈 내부 에서 전역 변 수 를 호출 하기 위해 서 는 다른 변 수 를 모듈 에 명시 적 으로 입력 해 야 합 니 다.
var module1 = (function ($, YAHOO) {
//...
})(jQuery, YAHOO);
위의
module1
모듈 은 jQuery 라 이브 러 리 와 YUI 라 이브 러 리 를 사용 해 야 합 니 다. 이 두 라 이브 러 리 (사실은 두 모듈) 를 매개 변수 로 입력 하 십시오 module1
.이렇게 하면 모듈 의 독립 성 을 확보 하 는 동시에 모듈 간 의 의존 관 계 를 뚜렷하게 한다.함 수 를 즉시 실행 하면 네 임 스페이스 의 역할 도 할 수 있다.
(function($, window, document) {
function go(num) {
}
function handleEvents() {
}
function initialize() {
}
function dieCarouselDie() {
}
//attach to the global scope
window.finalCarousel = {
init : initialize,
destroy : dieCouraselDie
}
})( jQuery, window, document );
상기 코드 에서
module1
대상 이 전체 로 수출 되 고 대외 노출 finalCarousel
과 init
인터페이스, 내부 방법 destroy
, go
, handleEvents
, initialize
은 모두 외부 에서 호출 할 수 없다.참조 링크
JavaScript Modules: A Beginner’s Guide, by Preethi Kasireddy
이 내용에 흥미가 있습니까?
현재 기사가 여러분의 문제를 해결하지 못하는 경우 AI 엔진은 머신러닝 분석(스마트 모델이 방금 만들어져 부정확한 경우가 있을 수 있음)을 통해 가장 유사한 기사를 추천합니다:
Fortinet FortiWeb Web Application Firewall Policy BypassFrom: Geffrey Velasquez Date: Wed, 2 May 2012 20:33:23 -0500...
텍스트를 자유롭게 공유하거나 복사할 수 있습니다.하지만 이 문서의 URL은 참조 URL로 남겨 두십시오.
CC BY-SA 2.5, CC BY-SA 3.0 및 CC BY-SA 4.0에 따라 라이센스가 부여됩니다.