常用数据类型与特点
**参考资料: **
JavaScript 数据类型和数据结构 - JavaScript | MDN (mozilla.org)
Null 类型
Null类型只有一个值: null
表示值为null
typeof null
==> 'object'
所以 typeof null === 'object' 值为 true, 因此,也可以将null视为一个特殊的对象
undefined 类型
undefined 类型只有一个值: undefined
表示未赋值。
typeof undefined
==> 'undefined'
let x;
var y;
let p:Person;
console.log(typeof x); // 'undefined'
console.log(typeof y); // 'undefined'
console.log(typeof p); // 'undefined'
扩展:在ts中使用未赋值的变量会有错误提示ts(2454)
Number 类型
数值类型,小数,整数,正数,负数 都通过该类型表示, 有最大和最小范围限制
范围
正数的最大值: Number.MAX_VALUE
正数的最小值: Number.MIN_VALUE
0
负数的最大值: -Number.MIN_VALUE
负数的最小值: -Number.MAX_VALUE
特殊值
特殊值: NaN, 当算数运算(如: 1/'a')的结果不是数值 或 parseInt(x), parseFloat(x) 的结果不是数值 时,会得到NaN结果
精度问题
使用Number进行算数运算会存在精度问题。如:
解决方式是使用 big.js 之类的库,来解决
常见需求
字符串转Number
数字字符串可以通过parseInt, parseFloat转换为Number类型
parseInt('3.2'); // 3
parseInt('01');// 1
parseInt('001');// 1
parseInt('a'); // NaN
parseFloat('3.2'); // 3.2
parseFloat('3'); // 3
parseFloat('3.0'); // 3
parseFloat('3.2'); // 3.2
parseFloat('03.2'); // 3.2
parseFloat('03.20') // 3.2
parseFloat('a'); // NaN
向上取整:Math.ceil
Math.ceil(2); // 2
Math.ceil(1); // 1
Math.ceil(1.0) // 1
Math.ceil(1.01) // 2
Math.ceil(1.2) // 2
向下取整:Math.floor
Math.floor(2) // 2
Math.floor(1) // 1
Math.floor(1.01) // 1
Math.floor(1.5) // 1
Math.floor(1.6) // 1
对第一位小数位四舍五入,保留整数位:Math.round
Math.round(2)// 2
Math.round(2.1) // 2
Math.round(2.16) // 2
Math.round(2.5) // 3
Math.round(2.6) // 3
保留n位小数,并对n+1位进行四舍五入:
/**
保留n位小数,四舍五入
@param num 待转换数值
@param n 需要保留的小数位数
*/
function toFixed(num, n){
const base = Math.pow(10,n)
return Math.round((num + Number.EPSILON) * base) / base;
}
toFixed(0,1) // 0
toFixed(1,0) // 1
toFixed(1,1) // 1
toFixed(0.1,1) // 0.1
toFixed(0.5,1) // 0.5
toFixed(0.6,1) // 0.6
toFixed(1.1,1) // 1.1
toFixed(1.5,1) // 1.5
toFixed(1.6,1) // 1.6
toFixed(1.61,1) // 1.6
toFixed(1.64,1) // 1.6
toFixed(1.65,1) // 1.7
toFixed(1.66,1) // 1.7
toFixed(1.649,1) // 1.6
toFixed(1.649,2) // 1.65
toFixed(1.649,3) // 1.649
toFixed(1.649,4) // 1.649
toFixed(1.649,5) // 1.649
保留n位小数,不四舍五入
/**
保留n位小数,不四舍五入
@param num 待转换数值
@param n 需要保留的小数位数
*/
function round(num, n){
const base = Math.pow(10,n)
return Math.floor(num * base) / base
}
round(0,0) //0
round(1,0) //1
round(0.1,0) //0
round(0.14,0) //0
round(0.15,0) //0
round(0.11,1) //0.1
round(0.14,1) //0.1
round(0.15,1) // 0.1
round(0.16,1) // 0.1
round(0.151,1) // 0.1
round(0.154,1) // 0.1
round(0.155,1) // 0.1
round(0.156,1) // 0.1
round(0.1,2) // 0.1
round(0.156,2) // 0.15
仅保留整数位:parseInt
parseInt(1.2) // 1
parseInt(1.5) // 1
parseInt(1.6) // 1
parseInt(1.56)// 1
日期:Date
常见需求
判断是否为日期类型
typeof new Date() // 'object'
日期对象的typeof结果是'object',因此,只能通过instanceof来判断值的类型是否为日期
new Date() instanceof Date // true
获取当前时间的日期对象
new Date()
获取当前时间/日期对象的时间戳
// 获取日期对象的时间戳
new Date().getTime()
// 获取当期时间的时间戳
Date.now()
字符串与日期对象相互转换
推荐采用 dayjs 库进行转换,推荐原因
- 中文文档齐全
- 支持ts
对象
获取对象所有key
console.log(Object.keys({ a: 1 }));
对象遍历
ts版本
interface Person {
name: string;
age: number;
}
let obj: Person = { name: "张三", age: 32 };
let key: keyof Person;
for (key in obj) {
console.log(typeof key, key, obj[key]);
}
js 版本
let obj = { name: "张三", age: 32 };
for (let key in obj) {
console.log(typeof key, key, obj[key]);
}
创建对象
字面量创建对象
const obj = { name:'张三' }
new object() 创建对象
const obj = new object()
obj['name']='张三';
obj.age=22;
class 创建对象
class Human{
constructor(name,age){
this.name = name
this.age = age
}
// 定义实例方法
say(fruit){
return `我是${this.name}, ${this.age}岁, 爱吃${fruit}`
}
// 定义静态方法
static eat(food){
return `我在吃${food}`
}
}
const h = new Human('张三',22)
h.say('菠菜') // '我是张三, 22岁, 爱吃牛奶'
Human.eat('水果') // 我在吃水果
构造函数创建对象
function Person(name,age){
this.name=name;
this.age=age
}
// 定义实例方法
Person.prototype.say = function(fruit){
return `我是${this.name}, ${this.age}岁, 爱吃${fruit}`
}
const per = new Person('张三',32)
// 定义静态方法
Person.eat=function(food){return `我在吃${food}`}
per.say('水果') // 我是张三,32岁,爱吃水果
Person.eat('水果')
数组
let x = []
let y = new Array()
常见需求
查找/过滤
过滤出所有满足条件的结果
[1,2,3,4,5].filter(x=>x>3) // [4,5]
查找第一个匹配的元素
[1,2,3,4,5].find(x=>x>3) // 4
查找第一个匹配元素的索引号
[1,2,3,4,5].findIndex(x=>x>3) // 3
排序
console.log(
[1, 4, 3, 2].sort((x: number, y: number) => {
return y - x;
})
);
// [ 4, 3, 2, 1 ]
反转
console.log([4, 3, 2].reverse()); // [ 2, 3, 4 ]
截取
console.log(["a", "b", "c", "d"].splice(1)); // [ 'b', 'c', 'd' ]
console.log(["a", "b", "c", "d"].splice(1, 2)); // [ 'b', 'c' ]
数组结构与树结构互换
数组结构转树结构
树结构转数组结构
拍平
// flat()默认拍平一级
console.log(["a", "b", [2, 3, ["j", "k"]], "c", "d"].flat());
// [ 'a', 'b', 2, 3, [ 'j', 'k' ], 'c', 'd' ]
// 指定拍平层级
console.log(["a", "b", [2, 3, ["j", "k"]], "c", "d"].flat(2));
// 拍平所有层级级
console.log(["a", "b", [2, 3, ["j", "k", [2, 0]]], "c", "d"].flat(Infinity));
数组去重
对于非对象组成的数组
const arr = [1, 2, 2, 'abc', 'abc', true, true, false, false, undefined, undefined, NaN, NaN]
const result = Array.from(new Set(arr))
console.log(result) // [ 1, 2, 'abc', true, false, undefined, NaN ]
对象组成的数组
function removeDuplicate(arr) {
const newArr = []
arr.forEach(item => {
if (!newArr.includes(item)) { // 这里需要使用对象的特定字段来判定是否重复
newArr.push(item)
}
})
return newArr
}
// 这里以非对象数组为例,你可以想象为对象数组
const arr = [1, 2, 2, 'abc', 'abc', true, true, false, false, undefined, undefined, NaN, NaN]
const result = removeDuplicate(arr)
console.log(result) // [ 1, 2, 'abc', true, false, undefined, NaN ]
求交集,并集,补集,差集
var a = [1,2,3,4,5]
var b = [2,4,6,8,10]
//交集
var intersect = a.filter(function(v){ return b.indexOf(v) > -1 })
//差集
var minus = a.filter(function(v){ return b.indexOf(v) == -1 })
//补集
var complement = a.filter(function(v){ return !(b.indexOf(v) > -1) })
.concat(b.filter(function(v){ return !(a.indexOf(v) > -1)}))
//并集
var unionSet = a.concat(b.filter(function(v){ return !(a.indexOf(v) > -1)}));
console.log("数组a:", a);
console.log("数组b:", b);
console.log("a与b的交集:", intersect);
console.log("a与b的差集:", minus);
console.log("a与b的补集:", complement);
console.log("a与b的并集:", unionSet);
Set和Map
function
Boolean 类型
包含两个值true, false
Boolean值用于条件运算:如: if...else, 三元运算, while, for等
其他类型的值可以通过!运算符转换为Boolean类型
undefined 转 Boolean
let x; // undefined
console.log(!x); // true
console.log(!!x);// false
if(x){console.log(1)}else {console.log(2)} // 2
null 转 Boolean
let x=null; // typeof x === 'null'
console.log(!x); // true
console.log(!!x);// false
if(x){console.log(1)}else {console.log(2)} // 2
number 转 Boolean
非0 转 Boolean
let x=3; // typeof x === 'number'
console.log(!x); // false
console.log(!!x);// true
if(x){console.log(1)}else {console.log(2)} // 1
0 转 Boolean
let x=0; // typeof x === 'number'
console.log(!x); // true
console.log(!!x);// false
if(x){console.log(1)}else {console.log(2)} // 2
数组 转 Boolean
let x=[]; // typeof x === 'object'
console.log(!x); // false
console.log(!!x);// true
if(x){console.log(1)}else {console.log(2)} // 1
对象 转 Boolean
let x={name:'张三'}; // typeof x === 'object'
console.log(!x); // false
console.log(!!x);// true
if(x){console.log(1)}else {console.log(2)} // 1