b2科目四模拟试题多少题驾考考爆了怎么补救
b2科目四模拟试题多少题 驾考考爆了怎么补救

深入了解js原型模式

电脑杂谈  发布时间:2020-04-16 05:29:24  来源:网络整理

c 原型模式_原型模式_原型模式(母题)

一,什么是原型模式

js中,创建对象的方法包括工厂模式和构造器模式. 构造器模式的最大问题是,构造器中的每个方法都需要在实例对象中重新创建原型模式,并且不能重用. 因此,为了解决此问题,您需要使用原型模式创建对象.

原型模式是将所有实例共享的方法和属性放在称为原型(prototype)的属性中. 创建函数时,将有一个原型属性. 该属性是指向对象的指针,该指针由构造函数创建的对象实例的原型对象调用.

// 构造函数
function Person() {};
// 原型属性prototype
Person.prototype.name = '张三';
Person.prototype.sayName = function() {
console.log(this.name);
};
let person1 = new Person();
person1.sayName(); //张三
let person2 = new Person();
person2.sayName(); // 张三
console.log(person1.sayName == person2.sayName); //true

1. 了解原型对象

每当创建一个新函数时,都会根据一组特定的规则为该函数创建一个原型属性. 该属性指向函数的原型对象. 默认情况下,所有原型对象都是自动获取构造函数(constructor)属性,该属性是指向原型属性所在函数的指针. 创建自定义构造函数后,其原型对象默认情况下将仅获得Constructor属性. 其他方法是从Object继承的.

当调用构造函数以创建新的实例对象时,实例将包含指向构造函数的原型对象的指针[[Prototype]]. 此连接存在于实例与构造函数的原型对象之间,而不存在于实例与构造函数之间.

每次代码读取对象的属性时原型模式,都会执行搜索,并且目标是具有给定名称的属性. 搜索从对象实例本身开始. 如果在实例中找到它,则返回该属性的值. 如果找不到,它将继续搜索指针指向的原型对象,并在原型对象中找到具有给定名称的属性. 该属性的值.

原型模式(母题)_原型模式_c 原型模式

尽管可以通过实例访问原型中存储的值,但是不能通过实例对象重写原型中的值. 如果将原型中具有相同名称的属性添加到实例,则该属性将自动屏蔽原型中的属性. 但是,原型中的属性不会被修改,只会阻止访问原型中的属性. delete运算符可以完全删除实例属性,以便可以再次访问原型中的属性.

2. 原型和操作符

hasOwnProperty()方法可以检测实例对象中是否存在属性,

// 构造函数
function Person() {
this.age = 16;
};
Person.prototype.name = "张三";
let person1 = new Person();
console.log(person1.hasOwnProperty('name')); // false
console.log(person1.hasOwnProperty('age')); // true

in运算符的使用可以分为两类,单独使用和在for-in循环中使用. 当单独使用in运算符时,可以通过对象访问给定的属性,无论该示例中是否存在该属性,该操作符都将返回true.

// 构造函数
function Person() {}
Person.prototype.name = 'zhang';
let person1 = new Person();
console.log('name' in person1); // true
person1.age = 14;
console.log('age' in person1); // true

同时使用hasOwnProperty()方法和in运算符,可以确定该属性是存在于原型还是对象中.

// 构造函数
function Person() {}
function hasPrototypeProperty(object, name) {
return !object.hasOwnProperty(name) && (name in object);
}
Person.prototype.name = "张三";
let person = new Person();
console.log(hasPrototypeProperty(person, 'name')); // true
console.log(hasPrototypeProperty(person, 'age')); // false

原型模式_c 原型模式_原型模式(母题)

使用for-in循环时,将返回所有可通过对象访问的可枚举属性,包括实例中存在的属性和原型中存在的属性.

let o = {
name: 'san',
age: 14,
};
for(let key in o) {
console.log(key);
}

要获取对象上的所有可枚举实例属性,可以使用Object.keys()方法,接收对象作为参数,并返回包含所有可枚举属性的字符串数组.

如果要获取所有实例属性. 不管它是否可枚举,都可以使用Object.getOwnPropertyNames()方法.

3. 更简单的原型语法

为了减少不必要的输入并在视觉上更好地封装原型的功能,通常的做法是使用包含所有属性和方法的对象文字重写整个原型对象.

// 构造函数
function Person() {};
Person.prototype = {
sayHi: function() {
console.log(hi);
},
name: '张三',
};

通过这种方式,原型对象中的Constructor属性将不再指向Person. 如果构造函数的值确实很重要,则可以按如下所示将其设置回适当的值.

原型模式_c 原型模式_原型模式(母题)

// 构造函数
function Person() {};
Person.prototype = {
constructor: Person,
sayHi: function() {
console.log(hi);
},
name: '张三',
};

但是,通过这种方式,对象的[[Enumerable]]属性设置为true. 默认情况下,构造函数属性不可枚举. 您可以通过Object.defineProperty()解决此问题

// 构造函数
function Person() {};
Person.prototype = {
sayHi: function() {
console.log(hi);
},
name: '张三',
};
Object.defineProperty(Person.prototype, "constructor", {
enumerable: false,
value: Person
}

4. 原型的动力

对原型对象所做的任何更改都可以立即从实例中反映出来.

function Person() {};
var friend = new Person();
Person.prototype.sayHi = function() {
console.log('hi');
};
friend.sayHi(); // hi

但是,如果重写整个原型对象,情况将有所不同. 调用构造函数时,会将指向原始原型的[[prototype]]指针添加到实例,并且将原型修改为另一个对象等效于切断构造函数和原始原型之间的连接. 示例中的指针仅指向原型,而不指向构造函数.

// 构造函数
function Person() {};
var friend = new Person();
Person.prototype = {
constructor: Person,
sayHi: function() {
console.log(hi);
}
};
friend.sayHi(); // Uncaught TypeError: friend.sayHi is not a function

原型模式(母题)_原型模式_c 原型模式

创建一个Person实例,然后重写其原型对象. 但是使用sayHi()时发生错误. 此时,实例所指向的原型对象是一个新对象. 重写原型对象切断了现有原型与先前存在的对象实例之间的直接联系. 所以我出错了.

5. 原生对象的原型

原型模型的重要性不仅体现在自定义类型的创建上,甚至所有本机引用类型都在此模式下使用,所有本机引用类型(对象,数组,字符串)等都在其构造函数中该方法在原型上定义. 您可以像修改自定义对象一样修改本机对象的原型.

二,原型模式的缺点

对于包含引用类型值的属性,默认情况下,所有实例将获得相同的属性值.

// 构造函数
function Person() {};
// 原型属性prototype
Person.prototype = {
constructor: Person,
friends: ['张三', '李四'],
}
let person1 = new Person();
let person2 = new Person();
person1.friends.push('王五');
console.log(person1.friends); // ["张三", "李四", "王五"]
console.log(person2.friends); // ["张三", "李四", "王五"]

由于好友存在于Person的原型对象中,因此person1对好友的修改也将通过person2反映出来,但实例对象通常具有自己的所有属性. 因此,很少有人单独使用原型. 创建对象的模式.

以上是本文的全部内容,希望对大家的学习有所帮助,并希望您支持脚本编写室.


本文来自电脑杂谈,转载请注明本文网址:
http://www.pc-fly.com/a/jisuanjixue/article-177230-1.html

    相关阅读
      发表评论  请自觉遵守互联网相关的政策法规,严禁发布、暴力、反动的言论

      热点图片
      拼命载入中...