JS启示录之原型
2024-01-11 18:23:19
在初学JavaScript的时候,我总是被“原型(链)”这个概念弄得晕头转向,面试题经常出现,网上也有很多关于它的文章。说实话,对于原型的理解固然很重要,但它算不上最难,甚至称不上“难点”,仅仅是一个必须懂的东西而已,不信?听我一一道来。
原型是什么?
原型是JavaScript中一个非常重要的概念,它是对象的一个特殊属性,指向创建该对象的构造函数。在JavaScript中,所有的对象都是通过构造函数创建的,而构造函数本身也是一个对象,所以构造函数也有原型。
function Person(name, age) {
this.name = name;
this.age = age;
}
const person = new Person('John Doe', 30);
console.log(person.constructor); // Person
console.log(person.constructor.prototype); // Person {}
从上面的代码中可以看出,person
对象的原型是Person
构造函数的原型对象。我们可以通过person.constructor.prototype
来访问它。
原型链是什么?
原型链是一个对象的原型对象的原型对象,依次类推。在JavaScript中,每个对象都有一个原型链,原型链的顶端是Object.prototype
对象。
console.log(person.__proto__); // Person {}
console.log(Person.prototype); // Person {}
console.log(Object.prototype); // {}
从上面的代码中可以看出,person
对象的原型链是Person.prototype
-> Object.prototype
。
原型链有什么用?
原型链的主要作用是实现继承。在JavaScript中,子类可以通过继承父类的原型对象来获得父类的属性和方法。
function Student(name, age, major) {
Person.call(this, name, age);
this.major = major;
}
Student.prototype = Object.create(Person.prototype);
const student = new Student('Jane Doe', 20, 'Computer Science');
console.log(student.name); // Jane Doe
console.log(student.age); // 20
console.log(student.major); // Computer Science
从上面的代码中可以看出,Student
类继承了Person
类的原型对象,因此Student
类的实例可以访问Person
类的属性和方法。
toString()方法
toString()
方法是JavaScript中一个内置的方法,它可以将一个对象转换为字符串。toString()
方法的默认行为是调用对象的[[Get]]
内部方法,该方法会沿着原型链向上查找,直到找到一个具有该属性的原型对象。如果找到,则返回该属性的值;否则,返回undefined
。
const person = new Person('John Doe', 30);
console.log(person.toString()); // "[object Person]"
const student = new Student('Jane Doe', 20, 'Computer Science');
console.log(student.toString()); // "[object Student]"
从上面的代码中可以看出,person
对象的toString()
方法返回了"[object Person]"
,而student
对象的toString()
方法返回了"[object Student]"
。这是因为person
对象的原型链中第一个具有toString()
属性的原型对象是Person.prototype
,而student
对象的原型链中第一个具有toString()
属性的原型对象是Student.prototype
。
利用toString()实现继承
我们可以利用toString()
方法来实现继承。我们可以将父类的toString()
方法复制到子类的原型对象中,这样子类的实例就可以访问父类的toString()
方法。
function Student(name, age, major) {
Person.call(this, name, age);
this.major = major;
}
Student.prototype = Object.create(Person.prototype);
Student.prototype.toString = Person.prototype.toString;
const student = new Student('Jane Doe', 20, 'Computer Science');
console.log(student.toString()); // "[object Person]"
从上面的代码中可以看出,student
对象的toString()
方法返回了"[object Person]"
。这是因为我们复制了Person.prototype
的toString()
方法到Student.prototype
中。
结语
原型(链)是JavaScript中一个非常重要的概念,它对于理解继承非常重要。通过原型链,我们可以实现子类继承父类的属性和方法。toString()
方法可以用来更方便的从原型链继承属性和方法。