JavaScript 函数的四种调用模式详解
本文深入解析 JavaScript 中函数的四种核心调用模式:函数模式、方法模式、构造器模式以及上下文模式。通过具体代码示例,详细阐述每种模式下 this 关键字的指向规则,重点讲解如何利用 call 和 apply 方法实现对象借用与上下文切换,帮助开发者准确理解并应用这些基础概念。
JavaScript 函数调用模式概述
在 JavaScript 开发中,理解函数的调用方式对于掌握语言特性至关重要。函数并非仅有一种调用形式,其内部 this 的绑定行为会随调用场景变化。本文将系统梳理 JavaScript 函数的四种主要调用模式,帮助开发者清晰区分不同语境下的执行逻辑。
函数模式:全局上下文下的调用
第一种模式为函数模式,这是最基础的调用方式。
当以独立函数的形式直接调用时,例如 fn(),函数内部的 this 默认指向全局对象。在浏览器环境中,this 即代表 window 对象;而在严格模式下,this 则为 undefined。
// 声明式函数
function fn1 () {
console.log(this);
}
// 函数表达式函数
var fn2 = function() {
console.log(this);
};
// 调用 函数中this表示全局对象,在浏览器中就是指window
fn1(); //window
fn2(); //window
方法模式:对象属性的调用行为
第二种模式称为方法模式,其核心特征是函数作为对象的属性存在。
当函数被赋值给对象的某个属性,并通过该对象进行调用时,便构成了方法调用模式。此时,函数内部的 this 关键字指向调用该方法的对象本身,而非全局对象。这种模式体现了面向对象编程中对象与行为的绑定关系。
var obj = {
name: "zhangSan",
sayHi: function () {
console.log(this);
}
};
obj.sayHi(); //obj对象
构造器模式:对象实例的创建过程
第三种模式是构造器调用模式,主要用于创建新对象实例。
该模式通过 new 关键字配合构造函数名及括号实现,例如 new Constructor()。其执行过程包含三个关键步骤:首先,在函数内部隐式创建一个空对象;其次,将该对象绑定为 this 并执行构造函数体内的代码;最后,若函数未显式返回复杂对象,则默认返回新创建的实例。需要注意的是,若构造函数手动返回基本数据类型,返回值仍为新对象;若返回复杂数据类型(如对象),则返回该显式指定的对象。
function Person() {}
var tom = new Person(); // 这就是构造器函数的调用
// 构造函数调用的详细过程
// 1 会在内部创建一个对象o
// 2 给对象赋值(this), 然后执行各种操作
// 3 返回这个对象o
// 构造函数的返回值:
//
// 有一个默认的返回值,新创建的对象(实例);
// 当手动添加返回值后(return语句):
// 1. 返回值是基本数据类型-->真正的返回值还是那个新创建的对象(即实例)
// 2. 返回值是复杂数据类型(对象)-->真正的返回值是这个对象
上下文模式:this 指向的控制与借用
第四种模式为上下文模式,其本质在于强制改变函数执行时的 this 指向。
这种模式允许一个对象借用另一个对象的方法,从而实现对 this 指向的自定义控制。这是实现代码复用和原型链扩展的重要手段。
在 JavaScript 中,实现上下文模式主要依赖 Function.prototype 提供的 call 和 apply 方法。任何函数均可调用这两个方法。它们接受第一个参数用于指定 this 的指向对象;后续参数用于传递原函数所需的参数。其中,call 方法要求参数逐个列出,而 apply 方法接受一个参数数组。
//Function.prototype.call ()
//Function.prototype.apply ()
//——>任何函数都可以调用call和apply方法
// 第一个参数控制this的指向,第二个参数:
在使用 上下文调用的 时候, 原函数(方法)可能会带有参数, 那么这个参数在上下文调用中使用 第二个( 第 n 个 )参数来表示
//伪数组
var o={ 0:10,1:20,length:2 };
//让o对象借用数组的push方法来添加元素
//[].push.call(o,30,50,70)
[].push.apply(o,[1,2,3])
console.log(o);//其中对象o中length属性的值也会改变的哦
通过上述四种模式的解析,我们可以看到 JavaScript 函数调用的灵活性与复杂性。掌握这些模式及其对应的 this 规则,是编写高质量、可维护代码的基础。
JavaScript入门书籍避坑:这些书不适合初学者
2026-11-05 16:31:15
JS使用Math.round实现保留两位小数的原理与代码
2026-11-05 15:35:55
JavaScript 原生 Date 对象怎么实现日期加减
2026-11-05 14:30:00
JavaScript函数定义的三种方式:声明、表达式与箭头函数
2026-11-05 13:50:55
JavaScript中escape、encodeURI和encodeURIComponent对空格的处理差异
2026-11-05 12:47:23
