文章目录
- 1. Promise.allSettled
- 2. Module 新增
- 2.1 ! 动态导入 import()
- 2.2 import.meta
- 2.3 export * as obj from 'module'
- 3. 字符串 matchAll()
- 4. BigInt
- 实际开发相关使用
- 5. globalThis
- 6. 空值合并运算符
- 7. 可选链操作符
1. Promise.allSettled
Promise.allSettled() 返回一个在所有给定的promise 都已经fulfilled 或rejected 后的promise ,并带有一个对象数组,每个对象表示对应的promise 结果。
之前学习的Promise.all 只有在所有的Promise 都已经fulfilled 或rejected 才会执行then() ,否则将执行catch()。
现在有一个聚合网站,需要请求其他网站的数据,如果使用Promise.all ,那么只要有一个网站数据未能传过来就会出错;但是我们现在想要只显示已经传过来的数据,也就是最后不会执行catch() ,只会执行then().
Promise.allSettled([ajax("1.json"),ajax("2.json"),ajax("33.json")])
then(res=>
// hideloading
console.log(res.filter(item=>item.status==="fulfilled"))
console.log()
})
2. Module 新增
2.1 ! 动态导入 import()
标准用法的import 导入的模块是静态的,会使所有被导入的模块,在加载时就被编译(无法做到按需编译降低首页加载速度)。有些场景中,你可能希望根据条件导入模块或者按需导入模块,这时你可以使用动态导入代替静态导入。
function login(){
return "普通"
let obtn = document.querySelector("#login")
obtn.onclick function(){
let role = login()
console.log(role)
render(role)
}
function render(role){
if(role === "管理员"){
// 加载1.js
import("./1.js")
}else{
// 加载2.js
import("./2.js")
}
import() 返回值是一个Promise 对象
async function render(role){
if(role === "管理员"){
// 加载1.js
let res1 = await import("./1.js")
console.log(res1)
}else{
// 加载2.js
let res2 = await import("./2.js")
console.log(res1)
}
在后续框架学习中我们一般将文件放入数组中,使用import() 按需导入文件。
2.2 import.meta
import.meta 会返回一个对象,有一个url 属性,返回当前模块的url 路径,只能在模块内部使用。
console.log("2.js加载了",import.meta)
2.3 export * as obj from ‘module’
export * as obj from ‘module’ 相当于无损无侵入的继承了某个文件
// 1.js
export default{
name:'111111'
}
export function testl(){
}
// 2.js
export default{
name:"22222"
}
export function test2(){
}
export * as obj1 from './1.js'
// html
<script type="module">
import* as obj from './2.js'
console.log(obj)
</script>
有时候我们需要别人的代码,但是不能改动,我们可以直接导入代码文件。
export* as obj3 from './3.js'
// export {obj3,test4} from './3.js'
// 只导入某个对象或方法
export function test4(){}
export default{
name:"444444"
}
3. 字符串 matchAll()
matchAll() 返回一个包含所有匹配正则表达式的结果的迭代器。可以使用for…of遍历,或者使用展开运算符(…)或者Array.from() 转换为数组。
let str = `
<u1>
<1i>11111</1i>
<1i>22222</1i>
<1i>33333</1i>
<1i>44444</1i>
</u1>
`
let reg = /<1i>(.*)<\/1i>/g
// \ 转义符
// g 表示全局
console.log(str.match(reg))
// 捕获 exec
let match = null
let list = []
while(match = reg.exec(str)){
console.log(match.groups.content)
list.push(match.groups.content)
}
console.log(list)
使用字符串的matchAll() 可以将全部捕获的内容拿出来。
let iobj = str.matchAll(reg)
for(let i of iobj){
console.log(i.groups.content)
}
4. BigInt
BigInt 是一种数据类型。
JavaScript 能够准确表示的整数范围在( − 2 53 -2^{53} −253 , 2 53 2^{53} 253)之间,超过这个范围,无法精确表示这个值,这使得JavaScript不适合进行科学和金融方面的精确计算。
为了与Number类型区别,Biglnt类型的数据必须添加后缀n。
let num1 = 123
let num2 = 123n
console.log(num1,num2)
console.log(num1 == num2)
console.log(num1 === num2)
// 简单的比较可以进行
console.log(num2 > 100)
console.log(num2 < 200)
// true
// false
// true
// true
BigInt 数据可以与Number 数据进行简单的比较,但是不可以进行加减乘除运算,会报错;只有转换为同种数据类型才可以进行运算
console.log(num2 + BigInt(2))
// BigInt 函数 -- 把Number 转换为BigInt
console.log(BigInt(2))
// 125n
// 2n
实际开发相关使用
id 一般都是较长的数字,如果从后端得到了Number 数据,对其进行进行加法运算,最大也只能得到 2 53 2^{53} 253,如果运算得到的数据实际上要更大,那么就会出现数据错误。
let jsonstr = {
"id":9007199254740993,
"1ist":[]
}
console.log(JSON.parse(jsonstr).id)
-
方案一
后端传入数据时就直接传入字符串数据 -
方案二 – 引入一个模块 json-bigint
先从github 中下载下来json-bigint 模块,但是这个模块不支持浏览器页面,需要创建vue 或者react 开发环境,或者使用Node 进行演示。
import JSONBigInt from 'json-bigint'
// 转换字符串操作
let JSONBigIntstr = JSONBigInt({storeAsstring: true })
let jsonstr = {
"id":9007199254740993,
"list":[]
}
console.log(JSONBigIntstr.parse(jsonstr))
- 方案三 –
let JSONBigIntNative = JSONBigInt({useNativeBigInt:true })
console.log(JSONBigIntNative.parse(jsonstr))
5. globalThis
globalThis – 顶层对象
globalThis 提供了一个标准的方式来获取不同环境下的全局this 对象(也就是全局对象自身)。不像window 或者self 这些属性,它确保可以在有无窗口的各种环境下正常工作。所以,你可以安心的使用globalThis,不必担心它的运行环境。为便于记忆,你只需要记住,全局作用域中的this就是globalThis。,
html 中使用window 可以拿到顶层对象;
webworker 中使用self 可以拿到顶层对象;
但globalThis 在html 或者 webworker 中使用都可以拿到相应的顶层对象。
if (typeof window !=='undefined'){return window;
if (typeof global !=='undefined'){return global;
throw new Error('unable to locate global object);
3;
let globals getGlobal()
if (globals.document){
conso1e.1og("进行dom操作相关")
else
conso1e.1og("不能进行dom操作")
// 现在
if (globalThis.Hocument){
console.1og("进行dom操作相关")
else
conso1e.1og("不能进行dom操作")
6. 空值合并运算符
空值合并运算符(??)是一个逻辑运算符。当左侧操作数为null 或undefined 时,其返回右侧的操作数;否则返回左侧的操作数。
let str1 = null ?? "kerwin"
console.log(str1)
let str2 = undefined ?? "kerwin"
console.log(str2)
// kerwin
// kerwin
这时我们可能会发现’ ?? ’ 跟|| 有些相似,相面代码演示的情况使用’ || ‘也是一样的结果。那么’ ?? '到底有什么区别呢?
let str3 = 0 ?? "kerwin"
console.log(str3)
let str4 = 0 || "kerwin"
console.log(str4)
let str5 = NaN || "kerwin"
console.log(str5)
// 0
// kerwin
// kerwin
?? 和 || 的区别是什么呢?
他们两个最大的区别就是 ‘’ 和0,??的左侧为 ‘’ 或者为 0 的时候,依然会返回左侧的值;
|| 会对左侧的数据进行boolean 类型转换,所以 ‘’ 和 0 会被转换成false ,返回右侧的值。
典型的实际应用就是个人信息页面的个性签名部分。用户个性签名为0 时就显示0 ,在未设置个性签名时才显示“这个人很懒,什么也没有留下”。
7. 可选链操作符
可选链前面的值如果是null 或undefined ,则不再执行后面的,之前返回可选链前面的值。
let obj = {
name:"kerwin",
// location:
// city:"dalian"
// }
// 如果对象没有location 属性,而你有调用了这个属性,那么程序就会报错
}
// 为了解决这个问题,之前的我们是写出了下面这行代码,意思是前者为假 那么就该步程序就不会向下执行
console.log(obj && obj.location && obj.location.city)
// 现在的操作 含义与之前的代码一样
console.log(obj?.location?.city ?? '北京')