函数调用方式
JavaScript 中调用函数的几种方式及 this 指向
问题
JavaScript 中,调用函数有哪几种方式?
解答
JavaScript 中有 4 种主要的函数调用方式,每种方式的 this 指向不同。
1. 普通函数调用
function greet(name) {
console.log(`Hello, ${name}!`);
console.log('this:', this);
}
// 直接调用
greet('Alice');
// 非严格模式:this 指向 window(浏览器)或 global(Node.js)
// 严格模式:this 为 undefined
2. 方法调用
const person = {
name: 'Bob',
sayHi() {
console.log(`Hi, I'm ${this.name}`);
}
};
// 作为对象方法调用
person.sayHi(); // Hi, I'm Bob
// this 指向调用该方法的对象
// 注意:方法赋值给变量后调用
const fn = person.sayHi;
fn(); // this 不再指向 person
3. 构造函数调用
function Person(name) {
this.name = name;
this.greet = function() {
console.log(`Hello, ${this.name}`);
};
}
// 使用 new 调用
const alice = new Person('Alice');
alice.greet(); // Hello, Alice
// this 指向新创建的实例对象
4. call / apply / bind 调用
function introduce(age, city) {
console.log(`I'm ${this.name}, ${age} years old, from ${city}`);
}
const user = { name: 'Tom' };
// call:参数逐个传递
introduce.call(user, 25, 'Beijing');
// I'm Tom, 25 years old, from Beijing
// apply:参数以数组传递
introduce.apply(user, [25, 'Beijing']);
// I'm Tom, 25 years old, from Beijing
// bind:返回绑定 this 的新函数
const boundFn = introduce.bind(user, 25);
boundFn('Shanghai');
// I'm Tom, 25 years old, from Shanghai
补充:箭头函数
const obj = {
name: 'Arrow',
// 箭头函数没有自己的 this
// 继承定义时外层作用域的 this
sayName: () => {
console.log(this.name); // undefined(this 指向外层)
},
sayNameNormal() {
const inner = () => {
console.log(this.name); // Arrow
};
inner();
}
};
obj.sayName();
obj.sayNameNormal();
关键点
- 普通调用:
this指向全局对象(严格模式为undefined) - 方法调用:
this指向调用方法的对象 - 构造函数调用:
this指向新创建的实例 - call/apply/bind:
this指向指定的对象 - 箭头函数:没有自己的
this,继承外层作用域
目录