面试题深扒JS原理与原型链:一道题搞定面试官
2023-12-17 16:10:56
一道面试题就能测出你的JavaScript水平?看似简单,实则不然。这道题不仅考察你对JavaScript基本概念的理解,还考验你对语言底层机制的洞察。一起来看看它到底有何玄机!
题干
已知以下代码:
function Person(name) {
this.name = name;
}
Person.prototype.sayName = function () {
console.log(this.name);
};
function Employee(name, department) {
Person.call(this, name);
this.department = department;
}
Employee.prototype = new Person(); // 关键代码
Employee.prototype.constructor = Employee;
const employee = new Employee('John', 'Engineering');
employee.sayName(); // "John"
试回答以下问题:
- 当调用
employee.sayName()
时,this
指向什么? Person.prototype
和Employee.prototype
有什么区别?- 在
Employee
构造函数中,为什么需要调用Person.call(this, name)
? Employee.prototype = new Person();
这句代码意味着什么?Employee.prototype.constructor = Employee;
这句代码为什么是必要的?
答案解析
1. 当调用employee.sayName()时,this指向什么?
当调用employee.sayName()
时,this
指向employee
对象。这是因为sayName()
方法定义在Employee.prototype
中,而employee
是Employee
的实例。因此,当调用employee.sayName()
时,this
会自动指向employee
对象。
2. Person.prototype和Employee.prototype有什么区别?
Person.prototype
是Person
函数的原型对象,而Employee.prototype
是Employee
函数的原型对象。原型对象是用来保存函数的所有实例共享的属性和方法。
Person.prototype
和Employee.prototype
的区别在于:
Person.prototype
只有sayName()
方法,而Employee.prototype
除了sayName()
方法外,还多了department
属性。Employee.prototype
的constructor
属性指向Employee
函数,而Person.prototype
的constructor
属性指向Person
函数。
3. 在Employee构造函数中,为什么需要调用Person.call(this, name)?
在Employee
构造函数中,需要调用Person.call(this, name)
来执行Person
函数的构造函数。这是因为Employee
函数继承了Person
函数,因此在创建Employee
实例时,需要先执行Person
函数的构造函数来初始化name
属性。
4. Employee.prototype = new Person();这句代码意味着什么?
Employee.prototype = new Person();
这句代码意味着Employee
函数的原型对象被重新赋值为一个新的Person
实例。这使得Employee
函数的原型对象能够继承Person
函数原型对象的所有属性和方法。
5. Employee.prototype.constructor = Employee;这句代码为什么是必要的?
Employee.prototype.constructor = Employee;
这句代码是必要的,因为它可以确保Employee
函数的实例的constructor
属性指向Employee
函数,而不是Person
函数。这对于确保Employee
函数的实例能够正确地调用Employee
函数的构造函数非常重要。
总结
这道面试题考察了JavaScript中的以下知识点:
- this的指向
- 原型(prototype)以及原型链
- 继承
- 引用
要解出这道题,需要对这些知识点有深入的理解。希望这篇文章能够帮助您更好地理解JavaScript中的这些关键概念。