대상을 위한 프로그램 설계 - 원형 모드


우리가 만든 모든 함수에는prototype 속성이 있다. 이 속성은 하나의 지침으로 하나의 대상을 가리킨다. 이 대상의 용도는 특정 유형의 모든 실례가 공유할 수 있는 속성과 방법을 포함한다. 통속적으로 말하면prototype은 함수를 구성하여 만든 실례 대상의 원형 대상이다. 원형 대상을 사용하는 장점은 모든 실례 대상이 그의 속성과 방법을 공유할 수 있다는 것이다.
 1     function Person(){ 2         Person.prototype.name = "Nicholas"; 3         Person.prototype.age = 29; 4         Person.prototype.job = "Software Engineer"; 5         Person.prototype.sayName = function(){ 6             console.log(this.name); 7         }; 8     }; 9 10     var person1 = new Person();11     person1.sayName(); //Nicholas12 13     var person2 = new Person();14     person2.sayName(); //Nicholas15 16     console.log(person1.sayName == person2.sayName); //true

 
1. 원형 대상을 이해할 때 언제든지 새로운 함수를 만들면 특정한 규칙에 따라prototype 속성을 만들고 이 속성은 함수의 원형 대상을 가리킨다.기본적으로 원형 대상은constructor 속성이 있고prototype 속성이 있는 함수 바늘을 가리킨다
isPrototypeOf() 메서드는 객체 간에 이러한 관계가 있는지 여부를 결정합니다.
 
1     console.log(Person.prototype.isPrototypeOf(person1)); //true

 
ECMAScript5에는 새로운 메서드 Object가 추가되었습니다.getPrototypeOf()
 
1 console.log(Object.getPrototypeOf(person1));//Object {name: "Nicholas", age: 29, job: "Software Engineer"}

 
코드가 대상의 속성을 읽을 때마다 검색을 실행합니다.먼저 검색은 대상 실례 자체부터 시작합니다.만약 실례 대상 자체에서 주어진 이름이 있는 속성을 찾았다면, 이 속성의 값을 되돌려주고, 찾지 못하면, 계속 바늘이 가리키는 원형 대상을 검색합니다
대상의 실례를 통해 원형에 저장된 값에 접근할 수 있으나 대상의 실례를 통해 원형의 값을 바꿀 수 없습니다. delete를 사용하면 실례 속성을 완전히 삭제하여 원형의 속성에 다시 접근할 수 있습니다.
 1     function Person(){ 2         Person.prototype.name = "Nicholas"; 3         Person.prototype.age = 29; 4         Person.prototype.job = "Software Engineer"; 5         Person.prototype.sayName = function(){ 6             console.log(this.name); 7         }; 8     }; 9 10     var person1 = new Person();11 12     var person2 = new Person();13 14     person1.name = "Greg";15     console.log(person1.name); //Greg16     console.log(person2.name); //Nicholas17 18     delete person1.name;19     console.log(person1.name); //Nicholas

 
hasOwnProperty () 방법은 속성이 실례에 있는지, 원형에 있는지, 실례에서true로 되돌아오는지 검사할 수 있습니다
 
 1     function Person(){ 2         Person.prototype.name = "Nicholas"; 3         Person.prototype.age = 29; 4         Person.prototype.job = "Software Engineer"; 5         Person.prototype.sayName = function(){ 6             console.log(this.name); 7         }; 8     }; 9 10     var person1 = new Person();11     var person2 = new Person();12     console.log(person1.hasOwnProperty("name")); //false13     person2.name = "Greg";14     console.log(person2.hasOwnProperty("name")); //true

 
2. 원형과 in 조작부호
두 가지 방식으로 in 조작부호를 사용하는데, 단독으로 사용하거나 for-in에서 사용하며, 단독으로 사용할 때, in 조작부호는 대상을 통해 지정한 속성에 접근할 수 있을 때true를 되돌려줍니다. 실례에서든 원형에서든.
 1     function Person(){ 2         Person.prototype.name = "Nicholas"; 3         Person.prototype.age = 29; 4         Person.prototype.job = "Software Engineer"; 5         Person.prototype.sayName = function(){ 6             console.log(this.name); 7         }; 8     }; 9 10     var person1 = new Person();11     var person2 = new Person();12     console.log(person1.hasOwnProperty("name")); //false13     console.log("name" in person1); //true14     person1.name = "Greg";15     console.log(person1.hasOwnProperty("name")); //true16     console.log("name" in person1); //true

 
hasOwnProperty()와 in 조작부호를 동시에 사용하면 이 속성이 실례에 존재하는지 원형에 존재하는지 확인할 수 있습니다
 
 1     function hasPrototypeProperty(object,name){ 2         return (!object.hasOwnProperty(name) && (name in object)); 3     } 4  5     //hasPrototypeProperty() true  6  7     function Person(){ 8         Person.prototype.name = "Nicholas"; 9         Person.prototype.age = 29;10         Person.prototype.job = "Software Engineer";11         Person.prototype.sayName = function(){12             console.log(this.name);13         };14     };15 16     var person3 = new Person();17     console.log(hasPrototypeProperty(person3,"job")); //true18     person3.job = "Teacher";19     console.log(hasPrototypeProperty(person3,"job")); //false

 
 
for-in 순환을 사용할 때 대상을 통해 접근할 수 있는 모든 열거 가능한 속성을 되돌려줍니다. 실례에 포함된 속성, 원형에 있는 속성, 원형에 있는 열거할 수 없는 속성을 차단하는 실례 속성을 포함합니다.객체의 모든 열거 가능한 속성을 가져오려면 ECMAScript5의 Object를 사용합니다.키스 () 방법, 이 방법은 하나의 대상을 매개 변수로 받아들여 모든 매개 속성을 포함하는 문자열 그룹을 되돌려줍니다.
 1     function Person(){ 2         Person.prototype.name = "Nicholas"; 3         Person.prototype.age = 29; 4         Person.prototype.job = "Software Engineer"; 5         Person.prototype.sayName = function(){ 6             console.log(this.name); 7         }; 8     }; 9 10     // Object.defineProperties(Person.prototype,{11     //     name:{12     //         enumerable: true,13     //     },14     //     age:{15     //         enumerable: true,16     //     },17     // });18 19     var keys = Object.keys(Person.prototype);20     console.log(keys);21     var person1 = new Person();22     person1.name = "Greg";23     person1.age = 22;24     var person1Keys = Object.keys(person1);25     console.log(person1Keys);

 
모든 실례 속성을 얻으려면, 열거할 수 있든 없든 Object를 사용할 수 있습니다.getOwnPropertyNames () 방법
1     var keys = Object.getOwnPropertyNames(Person.prototype);2     console.log(keys); //["constructor", "name", "age", "job", "sayName"]

 
 
3. 더 간단한 원형 문법은 모든 속성과 방법을 포함하는 대상의 글씨체로 전체 원형 대상을 다시 쓰는 것이다
 1     function Person(){ 2  3     } 4  5     Person.prototype = { 6         name : "Nicholas", 7         age : 29, 8         job : "SoftWare Engineer", 9         sayName : function(){10             console.log(this.name);11         },12     };

 
여기에 사용된 문법은 본질적으로 기본적인prototype 대상을 완전히 다시 썼기 때문에 constructor 속성도 새로운 대상의 constructor 속성(Object 구조 함수를 가리키는 것)이 되었다. 이때instanceof 조작부호는 정확한 결과를 되돌릴 수 있지만 constructor를 통해 대상의 유형을 확정할 수 없다.
1     var friend = new Person();2 3     console.log(friend instanceof Object); //true4     console.log(friend instanceof Person); //true5     console.log(friend.constructor == Person); //false6     console.log(friend.constructor == Object); //true

이 때 constructor 속성은 Object와 같습니다. constructor의 값이 중요하다면 적당한 값으로 설정할 수 있습니다
 1     function Person(){ 2  3     } 4  5     Person.prototype = { 6         constructor : Person, 7         name : "Nicholas", 8         age : 29, 9         job : "SoftWare Engineer",10         sayName : function(){11             console.log(this.name);12         },13     };

주의: 이런 식으로 constructor 속성을 다시 설정하면 그의'Enumerable'특성이true로 설정됩니다.기본적으로 원생 constructor 속성은 일일이 열거할 수 없습니다
 
4. 원형의 동태성
1     var friend = new Person();2     Person.prototype.sayHi = function(){3         alert("hi");4     };5     friend.sayHi(); //hi

 
friend 실례는 새로운 방법을 추가하기 전에 만들어졌지만, 코드가 대상의 속성을 읽을 때마다 검색을 실행하기 때문에 이 방법에 접근할 수 있습니다.먼저 검색은 대상 실례 자체부터 시작합니다.만약 실례 대상 자체에서 주어진 이름이 있는 속성을 찾았다면, 이 속성의 값을 되돌려주고, 찾지 못하면, 계속 바늘이 가리키는 원형 대상을 검색합니다
언제든지 원형에 속성과 방법을 추가할 수 있고 수정은 모든 대상의 실례에 즉시 반영될 수 있지만 전체 원형의 대상을 다시 쓴다면 상황은 달라진다
 1     function Person(){ 2     } 3  4     var friend = new Person(); 5  6     Person.prototype = { 7         constructor : Person, 8         name : "Nicholas", 9         age : 29,10         job : "SoftWare Engineer",11         sayName : function(){12             console.log(this.name);13         },14     };15 16     friend.sayName(); //error

 
 
5. 원생 대상 모델은 원생 대상의 원형을 통해 모든 기본 방법의 인용을 얻을 수 있을 뿐만 아니라 새로운 방법을 정의할 수 있다
1     String.prototype.ll = function(text){2         return text.length;3     };4     var msg = "Hello";5     console.log(msg.ll("SoftWare")); //8

 
6. 원형 대상의 문제는 먼저 구조 함수에 매개 변수를 전달하는 부분을 생략하고 그 결과 모든 실례가 기본적으로 같은 속성 값을 얻을 수 있다.원형 모델의 가장 큰 문제는 공유의 본성에 의해 발생한다. 기본값을 포함하는 속성은 실례에 같은 이름의 속성을 추가할 수 있지만 인용 유형을 포함하는 속성에 대해서는 문제가 비교적 두드러진다.
 1     function Person(){ 2     } 3  4     Person.prototype = { 5         constructor : Person, 6         name : "Nicholas", 7         age : 29, 8         job : "SoftWare Engineer", 9         friend : ["Shelby","Court"],10         sayName : function(){11             console.log(this.name);12         },13     };14 15     var person1 = new Person();16     var person2 = new Person();17 18     person1.friend.push("Van");19     console.log(person1.friend); //["Shelby", "Court", "Van"]20     console.log(person2.friend); //["Shelby", "Court", "Van"]21     console.log(person1.friend ==person2.friend); //true

이 문제는 바로 우리가 원형 모델을 단독으로 사용하는 사람이 매우 적은 이유이다
 
구조 함수 모드와 원형 모드를 조합하여 사용하다
 
 1     function Person(name,age,job){ 2         this.name = name; 3         this.age = age; 4         this.job = job; 5         this.friend = ["Shelby","Court"]; 6     } 7  8     Person.prototype = { 9         constructor : Person,10         sayName : function(){11             console.log(this.name);12         },13     };14 15     var person1 = new Person();16     var person2 = new Person();17 18     person1.friend.push("Van");19     console.log(person1.friend); //["Shelby", "Court", "Van"]20     console.log(person2.friend); //["Shelby", "Court"]21     console.log(person1.sayName === person2.sayName); //true

 
이것은 현재 ECMAScript에서 가장 광범위하게 사용되고 있는 사용자 정의 형식을 만드는 방법입니다. 이것은 인용 형식을 정의하는 기본 모델이라고 할 수 있습니다
동적 원형 모드
모든 정보를 구조 함수에 봉인하고 구조 함수에서 원형을 초기화함으로써 구조 함수와 원형을 동시에 사용하는 장점을 유지하였다
 
 1     function Person(name,age,job){ 2         this.name = name; 3         this.age = age; 4         this.job = job; 5         if(typeof this.sayName != "function"){  //  6             Person.prototype.sayName = function(){ 7                 console.log(this.name); 8             }; 9         };10     };11 12     var friend = new Person("Nicholas",29,"Software Engineer");13     friend.sayName(); //Nicholas

 
기생 구조 함수 모드
 
 1     function Person(name,age,job){ 2         var o = new Object(); 3         o.name = name; 4         o.age = age; 5         o.job = job; 6         o.sayName = function(){ 7             console.log(this.name); 8         }; 9         return o;10     }11 12     var friend = new Person("Nicholas",29,"Software Engineer");13     friend.sayName(); //Nicholas

 
이 모드는 특수한 상황에서 대상을 대상으로 구조 함수를 만듭니다. 만약 우리가 추가 방법을 가진 특수한 그룹을 만들고 싶다면
 1     function SpecialArray(){ 2         var values = new Array(); 3         values.push.apply(values,arguments); 4         values.toPipedString = function(){ 5             return this.join("|"); 6         }; 7         return values; 8     }; 9 10     var colors = new SpecialArray("red","blue","green");11     console.log(colors.toPipedString()); //red|blue|green

 
온당한 구조 함수 모드
이른바 온당한 대상이란 공공 속성이 없고 그 방법도this 대상을 인용하지 않을 만하다
 1    function Person(name,age,job){ 2  3        //  4        var o = new Object(); 5  6        //  7  8        //  9        o.sayName = function(){10            console.log(name);11        };12 13        // 14        return o;15 16    };17 18    var friend = Person("Nicholas",29,"Software Engineer");19    friend.sayName(); //Nicholas

이렇게 변수friend에는 온당한 대상이 저장되어 있으며,sayName () 방법을 호출하는 것 외에 데이터 구성원에 접근할 수 있는 다른 방법은 없습니다.

좋은 웹페이지 즐겨찾기