JS 高效、快速开发 代码片段 分类整理

JS 高效、快速开发 代码片段 分类整理

数组 / 对象 / 变量

1、删除数组中的重复值

删除数组的重复项是非常有必要的,使用“Set”会变得非常简单。

const removeDuplicates = (arr) => [...new Set(arr)]
console.log(removeDuplicates([1, 2, 2, 3, 3, 4, 4, 5, 5, 6])) 
// [1, 2, 3, 4, 5, 6]

2、删除数组对象的重复值

删除数组对象中重复项

const CSDN = [
	{ 
		id: '1', 
		result: '半' 
	},
  { 
		id: '1', 
		result: '半' 
	},
	{ 
		id: '2', 
		result: '生' 
	},
  { 
		id: '3', 
		result: '生' 
	},
	{ 
		id: '3', 
		result: '过' 
	},
  { 
		id: '3', 
		result: '往' 
	},
	{ 
		id: '4', 
		result: '往' 
	},
]

let obj = {}
let scdn = CSDN.reduce((cur,next) => {
    obj[next.id] ? "" : obj[next.id] = true && cur.push(next);
    return cur;
},[]) //设置cur默认类型为数组,并且初始值为空的数组
console.log(scdn );
// 0: {id: '1', result: '半'}
// 1: {id: '2', result: '生'}
// 2: {id: '3', result: '生'}
// 3: {id: '4', result: '往'}
// length: 4

3、展平一个数组

多层数组展开成一层

// 方法一:
const flat = (arr) =>
    [].concat.apply(
        [],
        arr.map((a) => (Array.isArray(a) ? flat(a) : a))
    )
    
// 方法二:
const flat = (arr) => arr.reduce((a, b) => (Array.isArray(b) ? [...a, ...flat(b)] : [...a, b]), [])

console.log( flat(['半', ['生', '过', ['往']]]) );
 // ['半', '生', '过', '往']

4、从数组中删除虚假值 / 过滤数组中值为 false 的值

使用此方法,您将能够过滤掉数组中的所有虚假值。

const removeFalsy = (arr) => arr.filter(Boolean)
console.log( removeFalsy([0, 'a string', '', NaN, true, 5, undefined, 'another string', false]) )
// ['a string', true, 5, 'another string']
const nums =[1,0, undefined,null,false];
const truthyNums = nums.filter(Boolean);
console.log(truthyNums) //[1]

5、清空数组

const numbers =[1,2,3,45]
numbers.length= 0
console.log(numbers)    //[]

6、取数组的最大数、最小数

const arr = [0, 1, 2, 3];
const min = Math.min(...arr);  // 0
const max = Math.max(...arr);  // 3

7、按功能分组数组

根据某些特征对数组进行分组

const groupBy = (arr, fn) => 
	arr.map(fn).reduce((acc, cur, i) => {
		acc[cur] = [...(acc[cur] || []), arr[i]];
		return acc;
	}, {});

console.log( groupBy([1, "2", 3, "4"],(val) => typeof val) )
//{ number: [ 1, 3 ], string: [ '2', '4' ] }

console.log(  groupBy([[1], [1,2], [3], [3,4]], (val) => typeof val.length) );
// { 1: [ [ 1 ], [ 3 ] ], 2: [ [ 1, 2 ], [ 3, 4 ] ] }
 

在这里插入图片描述

8、获取数组 、对象给定路径的值

const getValue = (from, selectors) =>
  selectors
    .replace(/\[([^[\]]*)]/g, '.$1.')
    .split('.')
    .filter((item) => item !== '')
    .reduce((acc, cur) => {
      if (acc instanceof Object) {
        return acc[cur];
      }
      return void 0;
    }, from);

const object = { a: [{ b: { c: 3 } }] };
const array = [{ a: { b: [1] } }, { c: 2 }];


console.log(getValue(object, 'a[0].b.c'));
// 3

console.log(getValue(array, '[0].a.b[0]'));
// 1

console.log(getValue(array, '[1].c'));
// 2

console.log(getValue(array, '[0].a.b[0][2].c'));
// undefined

在这里插入图片描述

9、随机打乱数组排序

对一个数组进行随机排列顺序

//随机的排列数组
const shuffleArray = (arr) => arr.sort(() => Math.random() - 0.5) 
// 测试
const arr = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];

console.log(shuffleArray(arr))
//[5, 2, 7, 6, 9, 8, 3, 10, 1, 4]

console.log(shuffleArray(arr))
//[6, 8, 10, 9, 3, 7, 1, 2, 4, 5]

console.log(shuffleArray(arr))
//[9, 5, 10, 4, 7, 8, 3, 2, 6, 1]

在这里插入图片描述

10、 对数组进行排序

使用 sort 方法对数组进行排序非常简单。

const number = [2,6,3,7,8,4,0];
number.sort();
// expected output: [0,2,3,4,6,7,8]

11、交换两个变量

[a, b] = [b, a]

let a = 1; 
let b = 2; 
console.log( [a, b] = [b, a] )// a = 2 b = 1 

12、校验数组是否为空

一行代码检查数组是否为空,将返回true或false

const isNotEmpty = arr => Array.isArray(arr) && arr.length > 0;
    
console.log( isNotEmpty([1, 2, 3]) );
//  true

13、数组 与 对象 克隆、合并

//克隆数组
const _arr = [0, 1, 2];
const arr = [..._arr];
// arr => [0, 1, 2]

//合并数组
const arr1 = [0, 1, 2];
const arr2 = [3, 4, 5];
const arr = [...arr1, ...arr2];
// arr => [0, 1, 2, 3, 4, 5];

//去重数组
const arr = [...new Set([0, 1, 1, null, null])];
// arr => [0, 1, null]
//克隆对象
const _obj = { a: 0, b: 1, c: 2 };
const obj = { ..._obj };
const obj = JSON.parse(JSON.stringify(_obj));
// obj => { a: 0, b: 1, c: 2 }

//合并对象
const obj1 = { a: 0, b: 1, c: 2 };
const obj2 = { c: 3, d: 4, e: 5 };
const obj = { ...obj1, ...obj2 };
// obj => { a: 0, b: 1, c: 3, d: 4, e: 5 }

14、 检查对象是否为空

const isEmpty = obj => Reflect.ownKeys(obj).length === 0 && obj.constructor === Object
console.log(isEmpty({}));  //true
console.log(isEmpty({id:1,name:"2"}));   //false

15、声明变量、变量赋值*

声明两个具有相同的值或相同类型的变量。

// 普通 
let test1;
let test2 = 1;

// 速写
let test1, test2 = 1;

给多个不同的变量赋值。

// 普通  
let test1, test2, test3;
test1 = 1;
test2 = 2;
test3 = 3;

// 速写
let [test1, test2, test3] = [1, 2, 3];

16、解构赋值

// 普通  
const test1 = this.data.test1;
const test2 = this.data.test2;
const test2 = this.data.test3;

// 速写
const { test1, test2, test3 } = this.data;

17、数组 find 简化

一个对象数组,根据对象属性找到特定对象,find 方法会非常有用。

const data = [{
        type: 'test1',
        name: 'abc'
    },
    {
        type: 'test2',
        name: 'cde'
    },
    {
        type: 'test1',
        name: 'fgh'
    },
]

// 普通  
findtest1 = name => {
    for (let i = 0; i < data.length; ++i) {
        if (data[i].type === 'test1' && data[i].name === name) {
            return data[i];
        }
    }
}

// 速写
filteredData = data.find(data => data.type === 'test1' && data.name === 'fgh');
console.log(filteredData); // { type: 'test1', name: 'fgh' }

18、将对象转换为对象数组。

Object.entries() 可以将对象转换为对象数组。

const data = { test1: 'abc', test2: 'cde', test3: 'efg' };
const arr = Object.entries(data);
console.log(arr);

// [ [ 'test1', 'abc' ],
//   [ 'test2', 'cde' ],
//   [ 'test3', 'efg' ]
// ]

Object.values() ES8 中引入的一个新特性,它的功能类似于 Object.entries(),只是没有键。

const data = { test1: 'abc', test2: 'cde' };
const arr = Object.values(data);
console.log(arr);

//   [ 'abc', 'cde']

19、 交换变量的值

let bears = 'bears'
let tigers = 'tigers '
[bears,tigers] =[tigers,bears]
console.log(bears) //tigers
console.log(tribes)  // bears

20、从数组中随机选择一个值

const elements =[2022, '半生',5, '过往'1'CSDN']
const random =(arr) => arr[Math.floor Math.random() * arr.length)]
const randomElement = random(elements)
console.log(randomElement)   // 2022 或 '半生' 或 5 或 '过往' 或 1 或 'CSDN'

21、冻结对象 让其不可改变

const octopus={
	tentacles: 8,
	color: 'blue',
}
Object.freeze(octopus)
octopus.tentacles= 10     // Error,不会改变
console.log(octopus) // {  tentacles: 8,color: 'blue'}

22、检查数组中的值

很多时候我们需要检查值是否存在于数组中,借助 include 方法。

const array1 = [1, 2, 3];
console.log(array1.includes(2));
// expected output: true

23、过滤数组

const words = ['spray', 'limit', 'elite', 'exuberant', 'destruction', 'present'];
const result = words.filter(word => word.length > 6);console.log(result);

// expected output: Array ["exuberant", "destruction", "present"]

24、生成数组

当你需要要生成一个0-99的数组

//  方案1
const createArr = (n) => Array.from(new Array(n), (v, i) => i)
const arr = createArr(100) // 0 - 99 数组

//  方案2
const createArr = (n) => new Array(n).fill(0).map((v, i) => i)
createArr(100) // 0 - 99数组

25、打乱数组

打乱这个数组的排序

const randomSort = list => list.sort(() => Math.random() - 0.5)
randomSort([0,1,2,3,4,5,6,7,8,9]) // 随机排列结果

26、数组去重

将数组中的所有重复的元素只保留一个

const removeDuplicates = list => [...new Set(list)]
removeDuplicates([0, 0, 2, 4, 5]) // [0,2,4,5]

27 、多数组取交集

当你需要取多个数组中的交集

const intersection = (a, ...arr) => [...new Set(a)].filter((v) => arr.every((b) => b.includes(v)))

intersection([1, 2, 3, 4], [2, 3, 4, 7, 8], [1, 3, 4, 9])
// [3, 4]

28、查找最大值、最小值索引

找到一个数组中的最大值的索引

const indexOfMax = (arr) => arr.reduce((prev, curr, i, a) => (curr > a[prev] ? i : prev), 0);
indexOfMax([1, 3, 9, 7, 5]); // 2

找到一个数组中的最小值的索引

const indexOfMin = (arr) => arr.reduce((prev, curr, i, a) => (curr < a[prev] ? i : prev), 0)
indexOfMin([2, 5, 3, 4, 1, 0, 9]) // 5

29、找到最接近的数值

在一个数组中找到一个最接近的值

const closest = (arr, n) => arr.reduce((prev, curr) => (Math.abs(curr - n) < Math.abs(prev - n) ? curr : prev))
closest([29, 87, 8, 78, 97, 20, 75, 33, 24, 17], 50) // 33

30、压缩多个数组(展开对应的索引合并)

将多个数组压缩成一个数组

const zip = (...arr) => Array.from({ length: Math.max(...arr.map((a) => a.length)) }, (_, i) => arr.map((a) => a[i]))
zip([1,2,3,4], ['a', 'b', 'c', 'd'], ['A', 'B', 'C', 'D'])
// [[1, 'a', 'A'], [2, 'b', 'B'], [3, 'c', 'C'], [4, 'd', 'D']]

31、矩阵交换行和列

将一个矩阵的行和列进行互相交换

const transpose = (matrix) => matrix[0].map((col, i) => matrix.map((row) => row[i]));
transpose(
    [              
        [1, 2, 3],
        [4, 5, 6], 
        [7, 8, 9], 
     ]             
 ); 
 // [
 //      [1, 4, 7],
 //      [2, 5, 8],
 //      [3, 6, 9],
 //  ]

字符串

1、生成随机字符串

我们可以使用 Math.random 生成一个随机字符串,当需要一个唯一的 ID 时非常方便。

const randomString = () => Math.random().toString(36).slice(2)
console.log( randomString() ) // gi1qtdego0b
console.log( randomString() )// f3qixv40mot
console.log( randomString() )// eeelv1pm3ja

2、字符串中每个单词的第一个字符大写

const uppercaseWords = (str) => str.replace(/^(.)|\s+(.)/g, (c) => c.toUpperCase())
console.log( uppercaseWords('hello world') ); // 'Hello World'

3、英文字符串首字母大写

const capitalize = str => str.charAt(0).toUpperCase() + str.slice(1)
    
console.log( capitalize("hello world"));// 'Hello world'

4、翻转字符串

可以使用 split、reverse 和 join 方法轻松反转字符串。

const reverse = str => str.split('').reverse().join('');
    
console.log( reverse('hello world') );     
// 'dlrow olleh'

5、截断字符串

在结尾处截断字符串
const truncateString = (string, length) => {
  return string.length < length ? string : `${string.slice(0, length - 3)}...`;
};

console.log(
  truncateString('Hi, I should be truncated because I am too loooong!', 36),
);
// Hi, I should be truncated because...
从中间截断字符串
const truncateStringMiddle = (string, length, start, end) => {
  return `${string.slice(0, start)}...${string.slice(string.length - end)}`;
};

console.log(
  truncateStringMiddle(
    'A long story goes here but then eventually ends!', // string
    25, // 需要的字符串大小
    13, // 从原始字符串第几位开始截取
    17, // 从原始字符串第几位停止截取
  ),
);
// A long story ... eventually ends!

6、获取字符串的字符

	let str = 'abc';
	// 普通
	str.charAt(2); // c
	
	// 速写
	str[2]; // c

时间

1、计算两个日期相差天数

计算两个日期之间的天数,一行代码就可以搞定。

const diffDays = (date, otherDate) => Math.ceil(Math.abs(date - otherDate) / (1000 * 60 * 60 * 24));
console.log( diffDays(new Date("2021-11-3"), new Date("2022-2-1"))   )// 100

2、从日期中获取一年中的哪一天

您想知道某个日期是一年中的哪一天吗?

const dayOfYear = (date) => Math.floor((date - new Date(date.getFullYear(), 0, 0)) / (1000 * 60 * 60 * 24))
console.log(  dayOfYear(new Date()) ) // 101

3、检查日期是否为周末

const isWeekend = (date) => [0, 6].indexOf(date.getDay()) !== -1;

console.log(isWeekend(new Date(2022, 4, 15)));
// false (Friday)
console.log(isWeekend(new Date(2022, 4, 16)));
// true (Saturday)

4、检查日期是否合法

使用以下代码段检查给定日期是否有效。

const isDateValid = (...val) => !Number.isNaN(new Date(...val).valueOf());
    
const isDateValid = (...val) => !Number.isNaN(new Date(...val).valueOf());
    
console.log(isDateValid("December 17, 1995 03:24:00")); //  true
console.log(isDateValid("1995.08.04 03:24:00")); //  true
console.log(isDateValid("1995/08/04 03:24:00")); //  true
console.log(isDateValid("1995/08/04 T 03:24:00")); //  aflse

5、以 hⓂ️s 格式记录时间

const timeFromDate = date => date.toTimeString().slice(0, 8);
    
console.log(timeFromDate(new Date(2021, 0, 10, 17, 30, 0))); 
// 17:30:00

6、等待一定时间后执行

const wait = async (milliseconds) => new Promise((resolve) => setTimeout(resolve, milliseconds));
const text = async () => {
  await wait (2000)
  console.log("你好,世界!");
}

console.log(text());

7、暂停一会

const pause = (millis) => new Promise(resolve => setTimeout(resolve, millis))
const fn = async () => {
  await pause(1000)
  console.log('fatfish') // 1s later
}
fn()

数字 / 格式化货币 / 格式化字节

1、获取两个数字之间的随机整数

此方法用于获取两个数字之间的随机整数。

const random = (min, max) => Math.floor(Math.random() * (max - min + 1) + min)
console.log( random(1, 50) )// 25
console.log( random(1, 50) )// 34

2、检查一个数字是偶数还是奇数

可以通过使用模运算符 (%) 来解决。

const isEven = num => num % 2 === 0
console.log( isEven(2) )// true
console.log( isEven(1) )// false

3、获取参数的平均值

我们可以使用 reduce 方法来获取我们在此函数中提供的参数的平均值。

const average = (...args) => args.reduce((a, b) => a + b) / args.length;
console.log( average(1, 2, 3, 4, 5);  )  // 3

4、将数字保留指定小数点位数

使用 Math.pow() 方法,我们可以将一个数字截断为我们在函数中提供的某个小数点。

const round = (n, d) => Number(Math.round(n + "e" + d) + "e-" + d)
console.log( round(1.005, 2)  ) //1.01
console.log( round(1.555, 2)  ) //1.56
console.log( round(1.554, 2)  ) //1.55
console.log( round(1.555, 3)  ) //1.555
console.log( round(1.555, 1)  ) //1.6
const num = 0.123456789
const fixed2 = num.toFixed(2)
const fixed3 = num.toFixed(3)
console.log(fixed2)  //0.12 
console.log(fixed3)  // 0.123

5、格式化货币(整数部分每3位用逗号分割)

不需要小数的情况
// 方法 1
function formatMoney(num) {
  return num.toLocaleString();
}

// 方法 2
function formatMoney(num) {
  const nf = new Intl.NumberFormat();
  return nf.format(num);
}

//方法 3
function formatMoney(num) {
  return num.toString().replace(/\B(?=(\d{3})+(?!\d))/g, ',');
}

// 方法 4
function formatMoney(num) {
  const arr = num.toString().split('');
  let index = -3;

  while (arr.length + index > 0) {
    arr.splice(index, 0, ',');
    index -= 4;
  }

  return arr.join('');
}


console.log('20220415' + formatMoney(20220316));
// '20,220,316'

在这里插入图片描述

支持小数

小数部分必须为2位,不足2位补零,多于2位四舍五入

const numFormat = new Intl.NumberFormat('zh-CN', { minimumFractionDigits: 2, maximumFractionDigits: 2 });

/**
 * 整数部分每3位用逗号分割。
 * 小数部分必须为2位,不足2位补零,多于2位四舍五入
 */
function formatCurrency(number) {
  return numFormat.format(number);
}

// 测试0
console.log('0转换成' + formatCurrency(0));
console.log('-0转换成' + formatCurrency(-0));
console.log('0.0转换成' + formatCurrency(0.0));
console.log('-0.0转换成' + formatCurrency(-0.0));

// 测试1位整数
console.log('3转换成' + formatCurrency(3));
console.log('-3转换成' + formatCurrency(-3));

// 测试3位整数
console.log('123转换成' + formatCurrency(123));
console.log('-123转换成' + formatCurrency(-123));

// 测试5位整数
console.log('12345转换成' + formatCurrency(12345));
console.log('-12345转换成' + formatCurrency(-12345));

// 测试7位整数
console.log('1234567转换成' + formatCurrency(1234567));
console.log('-1234567转换成' + formatCurrency(-1234567));

// 测试1位小数
console.log('12345.3转换成' + formatCurrency(12345.3));
console.log('-12345.3转换成' + formatCurrency(-12345.3));

// 测试2位小数
console.log('12345.34转换成' + formatCurrency(12345.34));
console.log('-12345.34转换成' + formatCurrency(-12345.34));

// 测试3位小数
console.log('12345.344转换成' + formatCurrency(12345.344));
console.log('-12345.344转换成' + formatCurrency(-12345.344));
console.log('12345.345转换成' + formatCurrency(12345.345));
console.log('-12345.345转换成' + formatCurrency(-12345.345));

在这里插入图片描述

6、格式化字节

将字节转换为可读文本时

const formatBytes = (bytes, decimals = 2) => {
  if (bytes < 0) return '';
  if (bytes <= 1) return `${bytes}B`;
  const k = 1024;
  const dm = decimals < 0 ? 0 : decimals;
  const sizes = ['B', 'KB', 'MB', 'GB', 'TB', 'PB', 'EB', 'ZB', 'YB'];
  const i = Math.floor(Math.log(bytes) / Math.log(k));
  return `${parseFloat((bytes / k ** i).toFixed(dm))}${sizes[i]}`;
};


console.log(formatBytes(1024));
// 1KB

console.log(formatBytes(1024 ** 2));
// 1MB

console.log(formatBytes(1024 ** 3));
// 1GB

console.log(formatBytes(1024 ** 4));
// 1TB

在这里插入图片描述

7、数字 转 大写汉字 及 其他汉字【万以下整数】

	const toChinesNum = (num) => {
        let changeNum = ['零', '一', '二', '三', '四', '五', '六', '七', '八', '九'];  
        // let changeNum =['零', '壹', '贰', '叁', '肆', '伍', '陆', '柒', '捌', '玖']
        let unit = ["", "十", "百", "千", "万"]; 
        // let unit =["", "拾", "佰", "仟", "万",];
        num = parseInt(num);
        let getWan = (temp) => {
            let strArr = temp.toString().split("").reverse();
            let newNum = "";
            for (var i = 0; i < strArr.length; i++) {
                newNum = (i == 0 && strArr[i] == 0 ? "" : (i > 0 && strArr[i] == 0 && strArr[i - 1] == 0 ? "" : changeNum[strArr[i]] + (strArr[i] == 0 ? unit[0] : unit[i]))) + newNum;
            }
            return newNum;
        }
        let overWan = Math.floor(num / 10000);
        let noWan = num % 10000;
        if (noWan.toString().length < 4) noWan = "0" + noWan;
        return overWan ? getWan(overWan) + "万" + getWan(noWan) : getWan(num);

    };


        console.log(toChinesNum(12345)); // 一万二千三百四十五

8、 指数幂简化

// 普通
Math.pow(2,3); // 8

// 速写
2**3 // 8

9、从数组中获取最大值和最小值

const nums =[1,2,3,4,5,-3,99,-45-1]
const max = Math.max( ...nums )
const min = Math.min( ...nums )
console.log(max)  //99
console.log(min)   //-45

10、进制转换

将十进制数字转换成其他N进制的数字,可以使用toString(n)

const toDecimal = (num, n = 10) => num.(n) 
// 假设数字10要转换成2进制
toDecimal(10, 2) // '1010'

将n进制数组转换成十进制,可以使用parseInt(num, n)

// 10的2进制为1010
const toDecimalism = (num, n = 10) => parseInt(num, n)
toDecimalism(1010, 2)

11、四舍五入

将小数点后的某些数字截断,并取四舍五入

const toFixed = (n, fixed) => `${n}`.match(new RegExp(`^-?\d+(?:.\d{0,${fixed}})?`))[0]
toFixed(10.255, 2) // 10.25

12、补零

在一个数字num不足len位数的时候前面补零操作

const replenishZero = (num, len, zero = 0) => num.().padStart(len, zero)
replenishZero(8, 2) // 08

13、数字正则

将手机号码格式化成xxx-xxxx-xxxx的形式

const formatPhone = (str, sign = '-') => str.replace(/(\W|\s)/g, "").split(/^(\d{3})(\d{4})(\d{4})$/).filter(item => item).join(sign)

formatPhone('13123456789') // '131-2345-6789'
formatPhone('13 1234 56 789', ' ') // '131 2345 6789'

将一段文本中的多个空格合并成一个空格

const setTrimOut = str => str.replace(/\s\s+/g, ' ')
const str = setTrimOut('hello,      jack') 
console.log(str);  //hello, jack

颜色

1、生成一个随机的十六进制颜色

如果你需要一个随机的颜色值,这个函数就可以了。

const randomColor = () => `#${Math.random().toString(16).slice(2, 8).padEnd(6, '0')}`
console.log(  randomColor() )// #9dae4f
console.log(  randomColor() )// #6ef10e

2、将RGB颜色转换为十六进制

//  方法一
const rgbToHex = (r, g, b) => "#" + ((1 << 24) + (r << 16) + (g << 8) + b).toString(16).slice(1)
console.log(  rgbToHex(255, 255, 255) ) // '#ffffff'
//  方法二
const rgbToHex =(r,g,b) => {
	const toHex = (num) => {
		const hex =num.toString(16)
		return hex.length ===1 ? `0${hex}` : hex
	}
	return `#${toHex(r)}${toHex(g)}${toHex(b)}`
}
console.log(rgbToHex(46,32,67))  //#2e2043

其他

1、清除所有cookies

const clearCookies = () => document.cookie.split(';').forEach((c) => (document.cookie = c.replace(/^ +/, '').replace(/=.*/, `=;expires=${new Date().toUTCString()};path=/`)))

2、深拷贝

深拷贝功能考虑了几乎各种极端情况

const deepClone = (obj, map = new WeakMap()) => {
  if (obj instanceof Date) return new Date(obj);
  if (obj instanceof RegExp) return new RegExp(obj);

  if (map.has(obj)) {
    return map.get(obj);
  }

  const allDesc = Object.getOwnPropertyDescriptors(obj);
  const cloneObj = Object.create(Object.getPrototypeOf(obj), allDesc);

  map.set(obj, cloneObj);

  for (const key of Reflect.ownKeys(obj)) {
    const value = obj[key];

    cloneObj[key] =
      value instanceof Object && typeof value !== 'function'
        ? deepClone(value, map)
        : value;
  }
  return cloneObj;
};

const symbolKey = Symbol('symbolKey');
const originValue = {
  num: 0,
  str: '',
  boolean: true,
  unf: void 0,
  nul: null,
  obj: { name: 'object', id: 1 },
  arr: [0, 1, 2],
  func() {
    console.log('function');
  },
  date: new Date(0),
  reg: new RegExp('/regexp/ig'),
  [symbolKey]: 'symbol',
};
Object.defineProperty(originValue, 'innumerable', {
  // writable is true to ensure that the assignment operator can be used
  writable: true,
  enumerable: false,
  value: 'innumerable',
});

// Create circular reference
originValue.loop = originValue;
// Deep Copy
const clonedValue = deepClone(originValue);

// Change original value
originValue.arr.push(3);
originValue.obj.name = 'newObject';

// Remove circular reference
originValue.loop = '';
originValue[symbolKey] = 'newSymbol';

console.log('originValue: ', originValue);
console.log('clonedValue: ', clonedValue);

在这里插入图片描述

3、将URL参数转换为对象

从 URL 获取参数

const getURLParams = (url) => {
  return (url.match(/([^?=&]+)(=([^&]*))/g) || []).reduce((acc, cur) => {
    const [k, v] = cur.split('=');
    const p = acc[k];

    acc[k] = p ? (Array.isArray(p) ? p : [p]).concat(v) : v;
    return acc;
  }, {});
};


console.log(getURLParams('google.com'));
//  {}

console.log(getURLParams('https://www.google.com/?name=1&age=2'));
//  { name: '1', age: '2' }

// 支持数组格式
console.log(getURLParams('https://www.google.com/?name=1&age=2&age=3'));
//  { name: '1', age: [ '2', '3' ] }

console.log(getURLParams('name=1&age=2'));
//  { name: '1', age: '2' }

在这里插入图片描述
或者更直接的

console.log(Object.fromEntries(new URLSearchParams(window.location.search)));

4、将HTML String转为DOM

将变量嵌入到 HTML 中,然后,通过函数将这些字符串转换成真实的 DOM

// 方法 1
const str2DOM = (str) => {
  const div = document.createElement('div');
  div.innerHTML = str;
  return div.firstElementChild;
}

// 方法 2
const str2DOM = (str) => {
  return new DOMParser().parseFromString(str, 'text/html').body
    .firstElementChild;
}

// 方法 3
const str2DOM = (str) => {
  return document.createRange().createContextualFragment(str);
}

// 方法 4
const str2DOM = (str) => {
  const div = document.createElement('div');
  div.insertAdjacentHTML('afterbegin', str);
  return div.firstElementChild;
}

// 测试
const main = (name) => {
  const str = `<h1>Hello ${name}</h1>`;
  const element = str2DOM(str);
  console.log('element: ', element);

  document.body.appendChild(element);
}

main('World');

在这里插入图片描述

5、复制到剪贴板

const copyToClipboard = (text) =>
  navigator.clipboard?.writeText && navigator.clipboard.writeText(text)
// 测试
copyToClipboard("Hello World!")
//Ctrl+V  可以粘贴 Hello World!

6、检测暗模式

const isDarkMode = () =>
  window.matchMedia &&
  window.matchMedia("(prefers-color-scheme: dark)").matches
// 测试
console.log(isDarkMode())   // false/true

7、滚动到顶部、底部

//滚动到页面顶部
//有很多方法可以将页面滚动到顶部。

const goToTop = () => window.scrollTo(0,0, "smooth");
//or
const scrollToTop = (element) => element.scrollIntoView({behavior: "smooth", block: "start"});
// scroll to bottom of the page
const scrollToBottom = () => window.scrollTo(0, document.body.scrollHeight);



//滚动到底部
const scrollToBottom = (element) =>
  element.scrollIntoView({ behavior: "smooth", block: "end" })

8、获取用户选择的文本

使用内置的getSelection 属性获取用户选择的文本。

const getSelectedText = () => window.getSelection().toString();
    
console.log(getSelectedText()); 

9、重定向到另一个 URL

location 是全局 window 对象上的一个方法,设置 href 属性的行为与用户点击链接的行为相同。
把当前页面跳到另一个地址

const redirect = url => location.href = url

console.log(redirect("https://www.baidu.com/"));

10、在网页上获取选定的文本

const getSelectedText = () => window.getSelection().toString()

在这里插入图片描述

11、检查用户是否在Apple设备上

const isAppleDevice = () => /Mac|iPod|iPhone|iPad/.test(navigator.platform);

console.log(isAppleDevice()); //     true/false

12、确定数据类型

可确定的类型:undefined、null、string、number、boolean、array、object、symbol、date、regexp、function、asyncfunction、arguments、set、map、weakset、weakmap

const  DataType =(tgt, type) => {
  const dataType = Object.prototype.toString.call(tgt).replace(/\[object (\w+)\]/, "$1").toLowerCase();
  return type ? dataType === type : dataType;
}
    console.log(DataType("test")); // "string"
    console.log(DataType(20220314)); // "number"
    console.log(DataType(true)); // "boolean"
    console.log(DataType([], "array")); // true
    console.log(DataType({}, "array")); // false

13、 带有多个条件的 if 语句

把多个值放在一个数组中,然后调用数组的 includes 方法。

// 普通
if (x === 'abc' || x === 'def' || x === 'ghi' || x ==='jkl') {
    console.log("半生过往")
}

// 速写
if (['abc', 'def', 'ghi', 'jkl'].includes(x)) {
   console.log("半生过往")
}

14、switch 简化

将条件保存在键值对象中,根据条件来调用。

// 普通  
switch (data) {
  case 1:
    test1();
  break;
  case 2:
    test2();
  break;
  case 3:
    test();
  break;
  // ...
}

// 速写
let data = {
  1: test1,
  2: test2,
  3: test
};
data[something] && data[something]();

15、条件查找简化

基于不同的类型调用不同的方法,可以使用多个 else if 语句或 switch,

// 普通 
if (type === 'test01') {
  test1();
}
else if (type === 'test02') {
  test2();
}
else if (type === 'test03') {
  test3();
}
else if (type === 'test04') {
  test4();
} else {
  throw new Error('Invalid value ' + type);
}

// 速写
let types = {
  test1: test1,
  test2: test2,
  test3: test3,
  test4: test4
};
let func = types[type];
(!func) && throw new Error('Invalid value ' + type); 
console.log( func() );

16、indexOf 的按位操作简化

查找数组的某个值时,可以使用 indexOf() 方法。但有一种更好的方法。

// 普通
if(arr.indexOf(item) > -1) { // item found 
}
if(arr.indexOf(item) === -1) { // item not found
}

// 速写
if(~arr.indexOf(item)) { // item found
}
if(!~arr.indexOf(item)) { // item not found
}

按位 ( ~ ) 运算符将返回 true(-1 除外),反向操作只需要!~。也可以使用 include() 函数。

if (arr.includes(item)) { 
// 如果找到项目,则为true
}

17、可选链操作符?.

可选链操作符( ?. ) 允许读取位于连接对象链深处的属性的值,而不必明确验证链中的每个引用是否有效。?. 操作符的功能类似于. 链式操作符,不同之处在于,在引用为空 (null 或者 undefined) 的情况下不会引起错误,该表达式短路返回值是 undefined。与函数调用一起使用时,如果给定的函数不存在,则返回 undefined

const player ={
	name: 'banshengguowang',
	rating:1000,
	click:()=>{
		return 'click'
	},
	pass:(teammate)=>{
		return `Pass to ${teammate}`,
	},
console.log(player ?. name)     // banshengguowang
console.log(player ?.click ?.())    //click
console.log(player ?.teammate?.()    // undefined

举例

if (res && res.data && res.data.success) {   
   //code
} 

相当于

  if (res?.data?.success) {
   //code
} 

18、空值合并操作符 ??

空值合并操作符?? 是一个逻辑操作符,当左侧的操作数为 null 或者 undefined 时,返回其右侧操作数,否则返回左侧操作数。

const nullval = null
const emptyString = ''
const someNum = 13

const a = nullval ?? 'A 默认值'
const b= emptyString ?? 'B 默认值'
const c= SomeNum ?? 'C 默认值'
console.log(a)  //A 默认值
console.log(b) //l   空字符串 不等于 null 或者 undefined
console.log(c) // 13

19、实现全屏

function fullScreen() {  
    const el = document.documentElement
    const rfs = 
    el.requestFullScreen || 
    el.webkitRequestFullScreen || 
    el.mozRequestFullScreen || 
    el.msRequestFullscreen
    if(typeof rfs != "undefined" && rfs) {
        rfs.call(el)
    }
}
fullScreen()

20、退出全屏

function exitScreen() {
    if (document.exitFullscreen) { 
        document.exitFullscreen()
    } 
    else if (document.mozCancelFullScreen) { 
        document.mozCancelFullScreen()
    } 
    else if (document.webkitCancelFullScreen) { 
        document.webkitCancelFullScreen()
    } 
    else if (document.msExitFullscreen) { 
        document.msExitFullscreen()
    } 
    if(typeof cfs != "undefined" && cfs) {
        cfs.call(el)
    }
}
exitScreen()

21、页面打印(打印当前页面时)

window.print()

22、阻止关闭事件

阻止用户刷新或关闭浏览器时,可以选择触发beforeunload事件,部分浏览器无法自定义文本内容。

window.onbeforeunload = function(){
    return '你确定离开当前页面吗?';
};

23、屏幕录制

const streamPromise = navigator.mediaDevices.getDisplayMedia()
streamPromise.then(stream => {
    var recordedChunks = [];// recorded video data
var options = { mimeType: "video/webm; codecs=vp9" };// Set the encoding format
    var mediaRecorder = new MediaRecorder(stream, options);// Initialize the MediaRecorder instance
    mediaRecorder.ondataavailable = handleDataAvailable;// Set the callback when data is available (end of screen recording)
    mediaRecorder.start();
    // Video Fragmentation
    function handleDataAvailable(event) {
        if (event.data.size > 0) {
            recordedChunks.push(event.data);// Add data, event.data is a BLOB object
            download();// Encapsulate into a BLOB object and download
        }
    }
// file download
    function download() {
        var blob = new Blob(recordedChunks, {
            type: "video/webm"
        });
        // Videos can be uploaded to the backend here
        var url = URL.createObjectURL(blob);
        var a = document.createElement("a");
        document.body.appendChild(a);
        a.style = "display: none";
        a.href = url;
        a.download = "test.webm";
        a.click();
        window.URL.revokeObjectURL(url);
    }
})

24、判断横竖屏

function hengshuping(){
    if(window.orientation==180||window.orientation==0){
        alert("Portrait state!")
    }
    if(window.orientation==90||window.orientation==-90){
        alert("Landscape state!")
    }
}
window.addEventListener("onorientationchange" in window ? "orientationchange" : "resize", hengshuping, false);

25、改变横竖屏的样式

<style>
	@media all and (orientation : landscape) {
	    body {
	        background-color: #ff0000;
	    }
	}
	@media all and (orientation : portrait) {
	    body {
	        background-color: #00ff00;
	    }
	}
</style>

26、本地图片预览

<div class="test">
    <input type="file" name="" id="">
    <img src="" alt="">
</div>
<script>
const getObjectURL = (file) => {
    let url = null;
    if (window.createObjectURL != undefined) { // basic
        url = window.createObjectURL(file);
    } else if (window.URL != undefined) { // webkit or chrome
        url = window.URL.createObjectURL(file);
    } else if (window.URL != undefined) { // mozilla(firefox)
        url = window.URL.createObjectURL(file);
    }
    return url;
}
document.querySelector('input').addEventListener('change', (event) => {
    document.querySelector('img').src = getObjectURL(event.target.files[0])
})
</script>

27、图片预加载

const images = []
function preloader(args) {
    for (let i = 0, len = args.length; i < len; i++) {  
        images[i] = new Image()  
        images[i].src = args[i]
    } 
}  
preloader(['1.png', '2.jpg'])

28、元素可编辑

需要编辑一个dom元素时,让它像textarea一样点击

<div contenteditable="true">here can be edited</div>

在这里插入图片描述

29、激活应用

当你在移动端开发时,你需要打开其他应用程序。location.href赋值也可以操作以下方法。

<a href="tel:12345678910">phone</a>
<a href="sms:12345678910,12345678911?body=hello">android message</a> 
<a href="sms:/open?addresses=12345678910,12345678911&body=hello">ios message</a>
<a href="wx://">ios message</a>

30、获取鼠标选择

const getSelectedText = () => window.getSelection().toString()

console.log(getSelectedText())

在这里插入图片描述

  • 6
    点赞
  • 65
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

半生过往

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值