>웹 프론트엔드 >JS 튜토리얼 >자바스크립트 시리즈 심층이해(26): 디자인 패턴의 생성자 패턴에 대한 자세한 설명_자바스크립트 스킬

자바스크립트 시리즈 심층이해(26): 디자인 패턴의 생성자 패턴에 대한 자세한 설명_자바스크립트 스킬

WBOY
WBOY원래의
2016-05-16 16:11:28806검색

소개

생성자에 대해서는 누구나 익숙하지만, 초보자라면 여전히 생성자가 무엇인지 이해하는 것이 필요합니다. 생성자는 특정 유형의 객체를 생성하는 데 사용됩니다. 생성자는 사용할 객체를 선언할 뿐만 아니라 객체가 처음 생성될 때 객체의 멤버 값을 설정하기 위해 매개변수를 허용할 수도 있습니다. 자신만의 생성자를 사용자 정의하고 그 안에 사용자 정의 유형 객체의 속성이나 메서드를 선언할 수 있습니다.

기본 사용법

자바스크립트에서는 일반적으로 인스턴스를 구현하기 위해 생성자를 사용합니다. 자바스크립트에는 클래스라는 개념이 없지만 특별한 생성자가 있습니다. new 키워드를 사용하여 정의된 함수를 호출하면 JavaScript에 새 개체를 만들고 싶다고 알릴 수 있으며 새 개체의 멤버 선언은 모두 생성자에 정의됩니다. 생성자 내에서 this 키워드는 새로 생성된 객체를 참조합니다. 기본적인 사용법은 다음과 같습니다.

코드 복사 코드는 다음과 같습니다.

기능 자동차(모델, 연식, 마일) {
This.model = 모델;
올해.년 = 년;
This.miles = 마일;
This.output= 함수 () {
          return this.model "Gone" this.miles "Kilometers";
};
}

var tom= new Car("삼촌", 2009, 20000);
var dudu= new Car("Dudu", 2010, 5000);

console.log(tom.output());
console.log(dudu.output());

위의 예는 매우 간단한 생성자 패턴이지만 몇 가지 문제가 있습니다. 우선, 상속을 사용하는 것은 매우 번거로운 작업입니다. 둘째, 객체가 생성될 때마다 출력()이 재정의되는 가장 좋은 방법은 Car 유형의 모든 인스턴스가 이 출력() 메서드를 공유하도록 하는 것입니다. 인스턴스 수 그렇다면 많은 메모리가 절약됩니다.

이 문제를 해결하려면 다음 방법을 사용할 수 있습니다.

코드 복사 코드는 다음과 같습니다.

기능 자동차(모델, 연식, 마일) {
This.model = 모델;
올해.년 = 년;
This.miles = 마일;
This.output= formatCar;
}

함수 formatCar() {
Return this.model "Gone" this.miles "Kilometers";
}


이 방법도 가능하지만 다음과 같은 더 나은 방법이 있습니다.

생성자 및 프로토타입

JavaScript의 함수에는 프로토타입이라는 프로토타입 속성이 있습니다. 객체를 생성하기 위해 생성자를 호출하면 새로 생성된 객체에서 생성자 프로토타입의 모든 속성을 사용할 수 있습니다. 이에 따르면 여러 Car 객체 인스턴스가 동일한 프로토타입을 공유할 수 있습니다. 위 예제의 코드를 확장해 보겠습니다.

코드 복사 코드는 다음과 같습니다.

기능 자동차(모델, 연식, 마일) {
This.model = 모델;
올해.년 = 년;
This.miles = 마일;
}

/*
참고: 여기서는 Object.prototype
대신 Object.prototype 메서드 이름을 사용합니다. 주로 정의된 프로토타입 프로토타입 객체를 다시 작성하는 것을 방지하는 데 사용됩니다
*/
Car.prototype.output= 함수 () {
Return this.model "Gone" this.miles "Kilometers";
};

var tom = new Car("삼촌", 2009, 20000);
var dudu = new Car("Dudu", 2010, 5000);

console.log(tom.output());
console.log(dudu.output());


여기서는 단일 인스턴스인 출력()을 모든 Car 개체 인스턴스에서 공유할 수 있습니다.

또한: 일반 함수와 구별하기 위해 생성자를 대문자로 시작하는 것이 좋습니다.

새것만 사용할 수 있나요?

위의 예는 모두 new를 사용하여 기능 자동차용 객체를 생성하는 유일한 방법입니까? 실제로 다른 방법도 있습니다. 두 가지를 나열하겠습니다.

코드 복사 코드는 다음과 같습니다.

기능 자동차(모델, 연식, 마일) {
This.model = 모델;
올해.년 = 년;
This.miles = 마일;
// 출력 내용 사용자 정의
This.output = 함수 () {
          return this.model "Gone" this.miles "Kilometers";
}
}

//방법 1: 함수 호출
Car("삼촌", 2009, 20000); //창 객체에 추가
console.log(window.output());

//방법 2: 다른 객체의 범위 내에서 호출
var o = new Object();
Car.call(o, "두두", 2010, 5000);
console.log(o.output())


이 코드의 방법 1은 약간 특별합니다. new를 사용하여 함수를 직접 호출하지 않으면 전역 개체 창을 가리킵니다.
코드 복사 코드는 다음과 같습니다.

//함수 호출
var tom = Car("삼촌", 2009, 20000);
console.log(typeof tom); // "정의되지 않음"
console.log(window.output()); // "삼촌이 20,000km를 걸었습니다"

이때 객체 tom은 정의되지 않았으며 window.output()은 결과를 올바르게 출력하지만 new 키워드를 사용하면 이러한 문제가 발생하지 않습니다.
코드 복사 코드는 다음과 같습니다.

//새 키워드 사용
var tom = new Car("삼촌", 2009, 20000);
console.log(typeof tom); // "객체"
console.log(tom.output()); // "삼촌이 20,000km를 걸었습니다"

강제 신규

위의 예는 new를 사용하지 않는 문제를 보여줍니다. 따라서 생성자가 new 키워드를 사용하도록 강제할 수 있는 방법이 있습니까? 대답은 '예'입니다. 위 코드는

코드 복사 코드는 다음과 같습니다.

기능 자동차(모델, 연식, 마일) {
If (!(이 Car 인스턴스)) {
         새 차 반납(모델, 연식, 마일);
}
This.model = 모델;
올해.년 = 년;
This.miles = 마일;
This.output = 함수 () {
          return this.model "Gone" this.miles "Kilometers";
}
}

var tom = new Car("삼촌", 2009, 20000);
var dudu = Car("두두", 2010, 5000);

console.log(typeof tom); // "객체"
console.log(tom.output()); // "삼촌이 20,000km를 걸었습니다"
console.log(typeof dudu); // "객체"
console.log(dudu.output()); // "두두는 5000km를 걸었습니다"


this의 인스턴스가 Car인지 판단하면 new Car를 반환할지, 아니면 코드를 계속 실행할지 결정할 수 있습니다. new 키워드를 사용하면 (이 인스턴스of Car)가 true이고 new인 경우 다음 매개변수 할당이 계속됩니다. (이 Car 인스턴스)는 사용되지 않으며 false이며 새 인스턴스가 반환됩니다.

원래 래퍼 기능

JavaScript에는 숫자, 문자열, 부울이라는 세 가지 기본 래퍼 함수가 있습니다. 때로는 둘 다 사용됩니다.

코드 복사 코드는 다음과 같습니다.

// 원래 래퍼 함수 사용
var s = new String("내 문자열");
var n = 새 번호(101);
var b = new Boolean(true);


// 추천합니다
var s = "내 문자열";
변수 n = 101;
var b = true;


이러한 래퍼 함수는 숫자 상태를 유지하려는 경우에만 사용하는 것이 좋습니다. 차이점은 다음 코드를 참조하세요.
코드 복사 코드는 다음과 같습니다.

// 원래 문자열
var Greeting = "안녕하세요";
// 분할() 메서드를 사용하여
분할 Greeting.split(' ')[0] // "안녕하세요"
// 기본 유형에 새 속성을 추가할 때 오류가 보고되지 않습니다.
Greeting.smile = true;
// 이 값을 얻을 수 있는 방법이 없습니다(이유는 18장 ECMAScript 구현에서 설명했습니다)
console.log(typeof Greeting.smile); // "정의되지 않음"

//원래 문자열
var Greeting = new String("안녕하세요");
// 분할() 메소드를 사용하여
분할 Greeting.split(' ')[0] // "안녕하세요"
// 래퍼 함수 유형에 새 속성을 추가해도 오류가 발생하지 않습니다
Greeting.smile = true;
// 새 속성에 정상적으로 액세스할 수 있습니다
console.log(typeof Greeting.smile); // "부울"

요약

이 장에서는 주로 생성자 패턴의 사용 방법과 호출 방법, new 키워드의 차이점에 대해 설명합니다. 사용 시 주의하시기 바랍니다.

참고: http://www.addyosmani.com/resources/essentialjsdesignpatterns/book/#constructorpatternjavascript

성명:
본 글의 내용은 네티즌들의 자발적인 기여로 작성되었으며, 저작권은 원저작자에게 있습니다. 본 사이트는 이에 상응하는 법적 책임을 지지 않습니다. 표절이나 침해가 의심되는 콘텐츠를 발견한 경우 admin@php.cn으로 문의하세요.