js中的小技巧
1. string 转换成数字
- 可以用 *1 转数字
- 常用: 也可以使用
+
来转化字符串为数字
把Boolean构造函数当做回调参数传入,遍历时的每一项又传入Boolean。
const compact = arr => arr.filter(Boolean);
compact([0, 1, false, 2, '', 3, 'a', 'e' * 23, NaN, 's', 34])
3. 双位运算符 ~~
可以使用双位操作符来替代 Math.floor()。双否定位操作符的优势在于它执行相同的操作运行速度更快。
Math.floor(4.9) === 4//true
// 简写为:
~~4.9 === 4//true
不过要注意,对整数来说 ~~ 运算结果与 Math.floor() 运算结果相同,而对于负数来说不相同:
~~4.5// 4
Math.floor(4.5)// 4
~~-4.5// -4
Math.floor(-4.5)// -5
4. 取整 | 0
1.3 | 0// 1
-1.9 | 0// -1'1.5' | 0// 1
'-1.2' | 0// -1
5. 字符串比较时间先后
var a = "2014-08-08";
var b = "2014-09-09";
console.log(a > b, a < b);
// false true
console.log("21:00" < "09:10");
// false
console.log("21:00" < "9:10");
// true时间形式注意补0
注意:因为字符串比较大小是按照字符串从左到右每个字符的charCode来的,但所以特别要注意时间形式注意补06. 精确到指定位数的小数
将数字四舍五入到指定的小数位数。使用 Math.round() 和模板字面量将数字四舍五入为指定的小数位数。 省略第二个参数 decimals ,数字将被四舍五入到一个整数。
const round = (n, decimals = 0) => Number(`${Math.round(`${n}e${decimals}`)}e-${decimals}`)
round(1.345, 2)// 1.35
round(1.345, 1)// 1.3
7. 数字补0操作
有时候比如显示时间的时候有时候会需要把一位数字显示成两位,这时候就需要补0操作,可以使用slice和string的padStart方法
const addZero1 = (num, len = 2) => (`0${num}`).slice(-len)
// ES6 字符串补位方法
const addZero2 = (num, len = 2) => (`${num}`).padStart( len, '0')
addZero1(3)// 03
addZero2(32,4)// 0032
8. Object [key]
虽然将 foo.bar 写成 foo ['bar'] 是一种常见的做法,但是这种做法构成了编写可重用代码的基础。许多框架使用了这种方法,比如element的表单验证。
请考虑下面这个验证函数的简化示例:
function validate(values) {
if(!values.first) return false;
if(!values.last) return false;
return true;
}console.log(validate({first: 'Bruce',last: 'Wayne'}));
// true
上面的函数完美的完成验证工作。但是当有很多表单,则需要应用验证,此时会有不同的字段和规则。如果可以构建一个在运行时配置的通用验证函数,会是一个好选择。
// object validation rules
const schema = {
first: {
required: true
},
last: {
required: true
}
}// universal validation function
const validate = (schema, values) => {
for (field in schema) {
if (schema[field].required) {
if (!values[field]) {
return false;
}
}
}return true;
}console.log(validate(schema, {first:'Bruce'}));
// false
console.log(validate(schema, {first:'Bruce',last:'Wayne'}));
// true
现在有了这个验证函数,我们就可以在所有窗体中重用,而无需为每个窗体编写自定义验证函数。
9. reduce方法同时实现map和filter
假设现在有一个数列,你希望更新它的每一项(map的功能)然后筛选出一部分(filter的功能)。如果是先使用map然后filter的话,你需要遍历这个数组两次。 在下面的代码中,我们将数列中的值翻倍,然后挑选出那些大于50的数。
const numbers = [10, 20, 30, 40];
const doubledOver50 = numbers.reduce((finalList, num) => {
num = num * 2;
if (num > 50) {
finalList.push(num);
}
return finalList;
}, []);
doubledOver50;
// [60, 80]
10. 统计数组中相同项的个数
很多时候,你希望统计数组中重复出现项的个数然后用一个对象表示。那么你可以使用reduce方法处理这个数组。
下面的代码将统计每一种车的数目然后把总数用一个对象表示。
let cars = ['BMW','Benz', 'Benz', 'Tesla', 'BMW', 'Toyota'];
let carsObj = cars.reduce((obj, name) => {
obj[name] = obj[name] ? ++obj[name] : 1;
return obj;
}, {});
carsObj;
// { BMW: 2, Benz: 2, Tesla: 1, Toyota: 1 }
11. 使用解构来交换参数数值
let param1 = 1;
let param2 = 2;
[param1, param2] = [param2, param1];
12. 接收函数返回的多个结果
在下面的代码中,我们从/post中获取一个帖子,然后在/comments中获取相关评论。由于我们使用的是async/await,函数把返回值放在一个数组中。而我们使用数组解构后就可以把返回值直接赋给相应的变量。
async function getFullPost(){
return await Promise.all([
fetch('/post'),
fetch('/comments')
]);
}
const [post, comments] = getFullPost();
13. 平铺多维数组
let arr = [1, 2, [3, 4], [5,6]];
let result = [].concat(...arr);
console.log(result) // [1,2,3,4,5,6]
【js中的小技巧】以上方法只适用于二维数组,如果是二维以上数组,通过递归实现
function spread(arr) {
let result = [].concat(...arr);
return result.some(item => Array.isArray(item)) ?
spread(result)
: result;
}
14. 格式化JSON代码
let obj = {
name: 'jack',
age: 12,
skill: ['play', 'song']
}
console.log(JSON.stringify(obj, null, 4));
{
"name": "jack",
"age": 12,
"skill": [
"play",
"song"
]
}
15. 整数转千分位三种方式
一、只转整数部分,如果有小数,只保留三位
- 方式1:
const number = 1234567890
const nf = new Intl.NumberFormat('us')
nf.format(number) //如果有小数,最多保留三位小数
// 1,234,567,890
typeof nf.format(number)
// string
- 方式2:
number.toLocaleString('us')
// 1,234,567,890
二、会把小数也转成千分位
// 会把小数为也转成千分位
const reg = /(\d{1,3})(?=(?:\d{3})+(?!\d))/g;
// 如果有小数,则只转小数位
const reg1 =/(\d)(?=(\d{3})+$)/g;
number.toString().replace(reg, '$1,')
// 1,234,567,890
三、只转整数部分,小数位不转
- 方式1:
function sep(n) {
let [i, c] = n.toString().split(/(\.\d+)/)
return i.split('').reverse().map((c, idx) => (idx+1) % 3 === 0 ? ',' + c: c).reverse().join('').replace(/^,/, '') + c
}
- 方式2:
function sep2(n){
let str = n.toString()
str.indexOf('.') < 0 ? str+= '.' : void 0
return str.replace(/(\d)(?=(\d{3})+\.)/g, '$1,').replace(/\.$/, '')
}
16. 获取时间戳的方式
- Date.parse()
// 返回自定义时间戳
Date.parse('2017/03/19')
// 返回当前时间的事件戳
Date.parse(new Date())
- Date.getTime()
new Date().getTime()
- +new Date()
+new Date()
- Date.now()
Date.now()
- new Date().valueOf()
new Date().valueOf()
17. 判断值是否为纯对象
function isPlainObject(obj) {
if (typeof obj !== 'object' || obj === null) return falselet proto = obj
while (Object.getPrototypeOf(proto) !== null) {
proto = Object.getPrototypeOf(proto)
}return Object.getPrototypeOf(obj) === proto
}
推荐阅读
- 热闹中的孤独
- 一个小故事,我的思考。
- 家乡的那条小河
- 一个人的碎碎念
- 野营记-第五章|野营记-第五章 讨伐梦魇兽
- 昨夜小楼听风
- JS中的各种宽高度定义及其应用
- 2021-02-17|2021-02-17 小儿按摩膻中穴-舒缓咳嗽
- 【译】20个更有效地使用谷歌搜索的技巧
- 基于微信小程序带后端ssm接口小区物业管理平台设计