JS相关知识总结(一)
总结下这段时间吸收的许多小知识,以备忘记后翻阅。
关于面向对象
面向对象特征:
- 具有唯一标识性
- 具有状态
- 具有行为
JS的面向对象和JAVA的实现思路不一样,JS是基于原型并非基于类。但是JS为了看起来更像JAVA,为此添加了一些特性。
抛开为了看起来像JAVA引入的特性,JS面向对象总结起来很简单:每个对象都有原型,对象上找不到属性就去自身原型上找,直到Object.prototype。
在ES3时代为了操作原型我们没有办法只能使用 new
但是ES5之后引入了专门操作原型的方法:
- Object.create()
- Object.setPrototypeOf()
- Object.getPrototypeOf()
这样我们就可以抛开类的概念直接面对原型来实现面向对象。
JS关于模拟JAVA的面向对象部分
在我的理解中有以下部分属于模拟JAVA的行为:
- function 可以被new调用
- 引入this机制
- instanceof 操作符
通过 new 调用函数主要做了三件事:
- 使用被new 调用的函数的prototype属性构造一个新对象
- 将新对象作为函数的this,调用该函数
- 如没有引用类型返回则返回这个新建的对象
上面就是在模拟JAVA中的类,在ES5中抛开new我们可以做到同样的事情,并且不会有让人以为这是一个类。
this更是复杂,一大批文章去解释JS中的this,由此也可以看出有些复杂。
JS中的数据类型
JS一共有7中数据类型:
- Null
- Undefined
- Number
- String
- Boolean
- Symbol (ES6新加)
- Object (引用类型)
7种数据类型又被分为两类:基本类型和引用类型。
怎么判断数据对应的是哪种数据类型呢?
总结有三种:typeof
、instanceof
和 Object.prototype.toString.call()
,这三种都有自己的特点。
typeof
基本上可以直接返回数据对应的类型,有两个例外,一个是 typeof null
返回 "object"
,另一个是 typeof function() {}
返回 "function"
instanceof
左边是一个对象右边是一个构造函数。
instanceof会遍历对象的原型,查找是否有函数的prototype属性。
我认为,检查数据是否是数组就很方便了 [] instanceof Array
,当然这个是有问题的,所以后面又提供了Array.isArray()
方法判断是否是数组。
Object.prototype.toString.call()
该方法提供的返回值十分详细,不仅会返回上面其中类型,还包括很多JS内置对象,例如:Array
,Date
,RegExp
等。
但是这个对象有个问题,会强制装箱。也就是说判断不出是基本类型还是引用类型,如果在意的话需要配合上typeof
。
Object.prototype.toString.call(1); // [object Number]Object.prototype.toString.call(new Number(1)); // [object Number]
返回值都一样。
关于装箱和拆箱
说道装箱和拆箱就要提及一下它的表象 – 隐式类型转换。
JS中隐式类型转换应用广泛,最臭名昭著的就是 ==
。还有当我们直接调用 str.indexOf
方法的时候,str明明是基本值还不报错就是装箱在起作用。
装箱
每个基本值都有一个对应的对象类,装箱就是将基本值转换为对应的对象类型。但是Symbol是不能通过new 调用的,所以我们要另想办法。
上面提到的Object.prototype.toString.call
会强制装箱:
function a() {return this;
}
a.call(Symbol()) // 查看打印
拆箱(toPrimitive)
拆箱会先调用对象的valueOf
方法,如果返回值是非基本值再调用toString
方法,返回值非基本值则报错。
还记得偏门的面试题么?
if (a == 2 && a == 3) {console.log(true);}
虽然是语言不好的一面,但也可以了解下。这里就用到了拆箱知识。
如果 a 是对象和基本类型做 ==
比较首先会对 a 拆箱,拆箱步骤如上所述。
let b = 1;
let a = {valueOf: () => ++b
}if (a == 2 && a == 3) {console.log(true);
}
这样就会打印出 true
。
自定义拆箱
关于拆箱最后想说的是现在可以自定义这个行为了。
let o = {[Symbol.toPrimitive]: () => "hello world"
};console.log('' + o);
Number
关于Number一直有一个疑问就是NaN到底是不是数字。typeof NaN
其实返回的是 number 。所以Not a Number 是一个 Number。
我们都知道JS中数字有精度问题:0.1 + 0.2 === 0.3
返回的是false。这个时候们就要借助 Number.EPSILON来帮我们判断,Math.abs(0.1 + 0.2 - 0.3) <= Number.EPSILON
。
JS中是区分 +0 和 -0 的,但是 +0 === -0
返回true。那么怎么区分+0 和 -0 呢,这也是polyfill Object.is() 需要考虑的问题。
我们可以通过用 +0 和 -0 做分母来区分:
1 / 0 === Infinity // true
1 / -0 === -Infinity // true
1 / 0 === 1 / -0 // false
函数
通过实际开发中我们可以知道,有的函数可以直接调用和使用new
调用,有的函数指能通过new
调用有的函数只能直接调用。
这背后是有机制在控制的。JS中的数据类型大体分为两种,一个是基本类型,一个是引用类型。那么按理说function不是基本类型那就是引用类型,引用类型就是只有对象,函数也是一个对象,为什么函数这个对象可以调用而其他对象不行呢?
是因为函数这个对象具有两个私有属性决定了上面的特性,我们并没有手段去定义和查看这两个私有属性。一个是 [[constructor]]
,另一个是 [[call]]
。分别决定了是否可以通过new调用和直接调用。
注:不能通过new调用函数例如 () => {}
箭头函数,不能直接调用的函数例如Image
这样的环境提供的函数。
总结于即刻时间重学前端栏目,winter说知识是免费的,教育是收费的,这边总结出来的应该算知识,教育还留在了栏目里。
JS相关知识总结(一)相关推荐
- Vue.js 相关知识(动画)
1. 简介 Vue 在插入.更新或移除 DOM 时,提供多种不同方式的过渡效果,并提供 transition 组件来实现动画效果(用 transition 组件将需执行过渡效果的元素包裹) 语法:&l ...
- moment.js相关知识总结
参考连接:https://www.jianshu.com/p/9c10543420de 转载于:https://www.cnblogs.com/song-zmin/p/11461501.html
- JS作用域相关知识(#精)
在学习<你不知道的JS>一书中,特将作用域相关知识在此分享一下: #说到作用域,就不得不提到LHS查询和RHS查询: 1)如果查询目的是对变量进行赋值,则使用LHS查询 2)如果查询目的是 ...
- js基础--数据类型检测的相关知识
欢迎访问我的个人博客:www.xiaolongwu.cn 前言 最近工作有点忙,好几天都没更新技术博客了. 周末起床打开有道云笔记,发现自己的博客todolist里躺了一堆只有名字的文件. 话不多说, ...
- Next.js踩坑入门系列(七) —— 其他相关知识
Next.js踩坑入门系列 (一) Hello Next.js (二) 添加Antd && CSS (三) 目录重构&&再谈路由 (四) Next.js中期填坑 (五) ...
- 汇编实验2.2 查找匹配字符串(附有详细注释和源代码和相关知识)
实验2.2 查找匹配字符串 实验要求: 程序接收用户键入的一个关键字以及一个句子.如果句子中不包含关键字则显示'No match!';如果句子中包含关键字则显示'Match',且把该字在句子中的位置用 ...
- 【提高系列】webpack相关知识
这次我们主要研究的是webpack框架的相关知识,webpack是一个打包构建的前端框架,用于解决前端开发的模块化问题. 应用场景和纵向比较 说到webpack,肯定你还会想到gulp和grunt这些 ...
- 了解js基础知识中的作用域和闭包以及闭包的一些应用场景,浅析函数柯里化
js基础知识中的作用域和闭包 一.作用域 1.作用域.自由变量简介 (1)作用域定义 (2)作用域实例演示 (3)自由变量定义 (4)自由变量实例演示 2.作用域链简介 (1)作用域链定义 (2)作用 ...
- 小程序 长按api_微信小程序API相关知识科普
微信小程序API(Application Programming Interface),即应用程序编程接口.API是一种接口函数,把函数封装起来,给开发者,这样好多的功能就不需要你去实现了,只要会调用 ...
最新文章
- 公平与精确同样重要!CMU提出学习公平表征方法,实现算法公平
- 使用 C++0x 时 make_shared 完美转发构造函数参数的测试编译器
- Attachment rename issue in Faas
- ExtJs中Store简介(秘籍)
- 微信小程序动态更改标题栏_微信小程序实现动态设置页面标题的方法【附源码下载】...
- 24-java版Spark程序读取ElasticSearch数据
- 【牛客网SQL篇】SQL必知必会
- C++——判身份证号码真伪
- Spring实战——FileSystemResource
- 制作HTML邮件邮箱注意问题和解决方案--兼容手机邮箱、电脑邮箱和邮件客户端
- Activity启动流程(二)system_server进程处理启动Activity请求
- 静静的推荐分数 20作者 陈越单位 浙江大学
- python 请假审批系统_请假审批系统
- em模型补缺失值_缺失值填补方法
- 函数,类模板全特化,偏特化
- 刻意练习+一万小时定律+异类
- Idea将Java文件导出jar包
- 智慧职教云答案在哪里找_智慧职教云课堂上的题答案在哪里能找到?
- CAN总线隔离器 插入式CAN总线隔离器
- 梯度爆炸和梯度消失的本质原因