探究v8中的包装类

对象

在 JavaScript 中,对象是一种复杂的数据类型 ,用于存储具有相关属性和方法的数据结构 。对象是基于键值对 的集合,其中键是字符串 (或者符号 Symbol),值可以是任何数据类型,包括函数,这些函数被称为对象的方法。

对象中属性的增加

我们先来看如下代码;

可以看到,我们用mrPeng.like = '章若楠'往对象mrPeng中添加了一个keylike,值为 '章若楠' 的属性;

但如果我们要是写成这样呢?

我们先定义了一个字符串abclike,再通过mrPeng.abc = '刘亦菲'往对象中添加属性,此时添加属性的key是什么呢?

可以看到,新增属性的key就为abc;并没有引用定义的字符串abc的值。这是因为在对象中,key只能是字符串类型 ;所以用.abc添加属性的方法就把abc当作字符串 传给了key

那可不可以把abc当成变量传给key呢?可以,只不过要换一种方式;

mrPeng[abc] = '刘亦菲',这是js中的一种语法,也可以往对象之中添加属性,[]允许使用变量作为属性名称

与传统方法不同的是,它把abc当作变量并找到它的值传给了key

对象中属性的删除

js中提供了delete的语法,用于删除对象中的属性;

可以看到,sex属性就被删除了。

对象的创建

创建对象字面量

在js中,最简单的创建对象的方法,那就是直接创建一个对象字面量;再给它添加上需要的属性和方法。

csharp 复制代码
// 创建对象字面量

var obj = {}

new Object()

除了对象字面量之外,我们还可以通过 Object()构造方法去实例化一个空对象

new XXX() 自定义的构造函数

再就是,我们可以自定义构造函数 ,用new方式去实例化一个对象:

实例化出来的对象如下:

new

在上篇文章中,我们已经介绍过new的过程了;在这里,我们还可以用另外一种更加通俗的方式来理解new的过程;

kotlin 复制代码
function Car(color) {
    this.name = 'su7'
    this.height = 1400
    this.lang = 5000
    this.weight = 1000
    this.color = color
}

// new 过程

// 先创建this空对象
var this = {}

// 执行函数中的代码,往this对象中添加属性
    this.name = 'su7'
    this.height = 1400
    this.lang = 5000
    this.weight = 1000
    this.color = color
    
// 返回this对象
return this

由于this指向的就是实例化的对象 ,故而我们可以直接把this当成实例化的对象;再向其中添加属性。

不通过new 实例对象

如果我们不使用new方法去实例化对象,那我们可以把new的过程直接写在构造函数里面;

在上面的这种形式中,也能够实例化一个对象。

包装类

在JavaScript中,包装类(Wrapper Classes)是一组特殊的构造函数 ,它们能够将基本数据类型(primitive types)封装成对象 。这样做的主要目的是为了让基本类型的值能够拥有属性和方法 。JavaScript提供了三个内置的包装类,分别对应三种基本数据类型:Number, String, 和 Boolean

原始数据类型

在js中,原始数据类型 (也称为基本数据类型或简单数据类型)是不可变的数据类型;主要分为以下几种:Number,String,Boolean,undefined,null,Symbol 和 BigInt;我们知道,原始值身上是不能有属性和方法的,属性和方法只有对象才能拥有。但是看着如下一段代码,你陷入了沉思;

str明明是字符串类型,那它怎么还能调用方法呢?实则不然,在原始数据类型中,Number,String 和 Boolean 都有内置的构造函数。

原始类型的内置方法

在js中,一切皆可看作对象 ;其实原始数据类型也是由它们自身内置的构造函数new出来的对象,如下图;

用上述方式构造出来的对象就是包装对象 ;这些包装对象具有与它们所封装的基本类型相对应的属性和方法 ,比如,字符串string能够调用.length方法去获取字符串的长度。

原始值上挂载属性

因为Number原始值我们可以把它看成是一个包装对象 ,当我们往原始值上挂载一个属性时,会发生什么呢?

在上面中,我们就往num上面挂载了一个len属性为3,但是打印的时候,输出了undefined

这是因为在JavaScript中,当你尝试在一个原始值上添加属性时,实际上是在创建并操作一个临时的包装对象 。但是,这种添加的属性不会持久存在,一旦操作完成,这个临时的包装对象就会被销毁,所以你添加的属性似乎"消失"了。这是因为原始值本身不支持属性的挂载

valueOf 返回对象的"原始值"

在JavaScript中,valueOf 方法是一个内置的方法,几乎所有的对象都有这个方法。valueOf 的主要作用是返回对象的"原始值" 。这个方法通常用于将对象转换为其代表的原始数据类型 ,尤其是当对象被设计为封装某种基本数据类型的时候

ini 复制代码
var str = 'abc' // new String('abc')
str += 1 // str = 'abc1'
var test = typeof(str) // 'string'
if (test.length === 6) {
    test.sign = 'typeOf的返回结果可能是String'
    // new String(test).sign = 'xxxx'
    // valueOf(test)  判断是否为原始值类型
    // delete test.sign
}
console.log(test.sign); // new String(test).sign  undefined

每当你往原始值身上挂载属性时,包装对象的valueOf内置方法就会返回它的原始值;如果是原始类型,v8引擎会把原始值身上添加的属性给delete移除掉;因为在v8看来,原始值是不能拥有属性和方法的。

小结

在原始值对象中,当v8执行到包装类时,会通过valueOf方法试探该包装类是不是原始值 ,如果是,则秉承原始值不用具有属性和方法的 这一规则,再移除掉给包装类添加的属性

相关推荐
开开心心就好33 分钟前
电脑息屏工具,一键黑屏超方便
开发语言·javascript·电脑·scala·erlang·perl
江号软件分享34 分钟前
有效保障隐私,如何安全地擦除电脑上的敏感数据
前端
web守墓人2 小时前
【前端】ikun-markdown: 纯js实现markdown到富文本html的转换库
前端·javascript·html
Savior`L2 小时前
CSS知识复习5
前端·css
许白掰2 小时前
Linux入门篇学习——Linux 工具之 make 工具和 makefile 文件
linux·运维·服务器·前端·学习·编辑器
中微子6 小时前
🔥 React Context 面试必考!从源码到实战的完整攻略 | 99%的人都不知道的性能陷阱
前端·react.js
秋田君7 小时前
深入理解JavaScript设计模式之命令模式
javascript·设计模式·命令模式
中微子7 小时前
React 状态管理 源码深度解析
前端·react.js
风吹落叶花飘荡8 小时前
2025 Next.js项目提前编译并在服务器
服务器·开发语言·javascript
加减法原则8 小时前
Vue3 组合式函数:让你的代码复用如丝般顺滑
前端·vue.js