JS的引用类型有如下几种:
常见的引用类型有:Object,Array,Function
引用类型的特点
对于基本类型变量来说,系统会为其分配一块内存,这块内存中保存的,就是变量的内容。
对于引用类型变量来说,其存储的只是一个地址而已,这个地址指向的内存块才是是变量的真正内容。引用变量的赋值,也只是把地址进行传递(复制)。举个例子:
// a 和 b 指向同一块内存
var a = [1,2,3];
var b = a;
a.push(4);
console.log(b); // [1,2,3,4]
还有一点需要注意,JS中的函数传参,其实是按值传递(按引用传递)。举个例子:
// 函数f的入参,其实是把 a 的值复制了一份。注意 a 是一个引用类型变量,其保存的是一个指向内存块的一个地址。
function f(obj) {
obj.b = 1;
}
var a = { a : 1};
f(a);
console.log(a); // { a: 1, b: 1}
由于引用类型的存在,下面的代码是不会报错的:
// const 声明一个不可改变的变量。
// a 存储的只是数组的内存地址而已,a.push 并不会改变 a 的值。
const a = [];
a.push('1');
console.log(a); // ['1']
引用类型的判断
常常使用typeof
判断一个类型是基本类型还是引用类型:
var a;
typeof a; // undefined
a = null;
typeof a; // object
a = true;
typeof a; // boolean
a = 666;
typeof a; // number
a = "hello";
typeof a; // string
a = Symbol();
typeof a; // symbol
a = function(){}
typeof a; // function
a = [];
typeof a; // object
a = {};
typeof a; // object
在JS中所有的引用类型本质上都是对象,所以使用typeof
判断引用类型时都会得到object
,不能判断出具体的引用类型是什么。
instanceof:用来判断某个构造函数的 prototype 属性所指向的对象是否存在于另外一个要检测对象的原型链上简单说就是判断一个引用类型的变量具体是不是某种类型的对象:
({}) instanceof Object // true
([]) instanceof Array // true
(/aa/g) instanceof RegExp // true
(function(){}) instanceof Function // true
强引用&弱引用
- 一般来说,在 JavaScript 中,对象的引用是强保留的,这意味着只要持有对象的引用,它就不会被垃圾回收。
- 在 Javascript 中,WeakMap 和 WeakSet 是弱引用对象的唯一方法:将对象作为键添加到 WeakMap 或 WeakSet 中,是不会阻止它被垃圾回收的。
如何实现 JS 真正意义上的弱引用?
https://www.infoq.cn/article/lKsmb2tlGH1EHG0*bbYg