JS函数中参数的传递方式

10,128 阅读2分钟

无论是什么编程语言,函数的传参方式一般都有两种方式:一种按值传递,另外一种按引用传递;今天我们具体来说一下JS中这两种传参方式。

在介绍传值方式之前,先说一下js中数据类型,分为基本类型和引用类型:

  • 基本类型:undefined、Null、Boolean、Number、String、Symbol
  • 引用类型:Object

两种类型的数据最本质的区别是基本类型直接存储的变量的值,而引用类型存储的是变量的应用地址。下面开始介绍js中函数传值方式:

1、按值传递

按值传递说的就是参数都是基础类型,直接传递参数的数值。举例如下:

function getNum(num) {
    num = num + 2; 
    return num; 
} 
let num = 1; 
let result = getNum(num); 
console.log(num); // 1
console.log(result); // 3

这个很好理解了,因为num是基本数据类型,传值时直接拷贝字面量给参数,所以在函数执行后num原来的数据大小是不会发生变化的,函数中存储的仅仅是num的一个副本而已。

2、引用传值

引用传值,实际上传递的是参数的地址,而非数值。在方法调用时,实际的参数是对象(或者数组),这时js函数中的参数args的值会保存实际参数的地址。

举例如下:
var person = {name:'yimao'};
function foo(obj) {
  obj.name = 'ermao';
}
foo(person);
console.log(person.name); // 输出结果为:ermao

为何改变函数参数obj中name的值,person中的name也会发生改变呢,是因为obj与person指向的是同一个内存地址,所以obj中name改变会引起person中name的改变。

变形举例(常常会在面试中遇到)
function func(o) {
  o.name = "yimao"
  o = new Object()
  o.name = "sanmao"
} 
let obj = new Object();
func(obj);
console.log(obj.name); // yimao

为什么会打印yimao?因为在进入函数开始时对象obj和参数o是指向同一个内存地址的,代表的是同一个对象,此时设置o.name = "yimao",obj中的name也会被修改为name。但是函数中第二句o = new Object()将o的地址指向了另外一个新对象,所以o指向的对象不再是obj指向的对象,所以改变o中name的值不会影响到obj中属性的值,因此打印结果为yimao。