JS 工具函数
1、校验数据类型
1 2 3 | export const typeOf = function (obj) { return Object.prototype.toString.call(obj).slice(8, -1).toLowerCase() } |
示例:
1 2 3 4 5 6 | typeOf( '树哥' ) // string typeOf([]) // array typeOf( new Date()) // date typeOf( null ) // null typeOf( true ) // boolean typeOf(() => { }) // function |
2、防抖
1 2 3 4 5 6 7 | export const debounce = (() => { let timer = null return (callback, wait = 800) => { timer&&clearTimeout(timer) timer = setTimeout(callback, wait) } })() |
示例:
如 vue 中使用
1 2 3 4 5 6 7 | methods: { loadList() { debounce(() => { console.log( '加载数据' ) }, 500) } } |
3、节流
1 2 3 4 5 6 7 8 9 10 | export const throttle = (() => { let last = 0 return (callback, wait = 800) => { let now = + new Date() if (now - last > wait) { callback() last = now } } })() |
4、手机号脱敏
export const hideMobile = (mobile) => { return mobile.replace(/^(\d{3})\d{4}(\d{4})$/, "$1****$2") }
5、开启全屏
1 2 3 4 5 6 7 8 9 10 11 | export const launchFullscreen = (element) => { if (element.requestFullscreen) { element.requestFullscreen() } else if (element.mozRequestFullScreen) { element.mozRequestFullScreen() } else if (element.msRequestFullscreen) { element.msRequestFullscreen() } else if (element.webkitRequestFullscreen) { element.webkitRequestFullScreen() } } |
6、关闭全屏
1 2 3 4 5 6 7 8 9 10 11 | export const exitFullscreen = () => { if (document.exitFullscreen) { document.exitFullscreen() } else if (document.msExitFullscreen) { document.msExitFullscreen() } else if (document.mozCancelFullScreen) { document.mozCancelFullScreen() } else if (document.webkitExitFullscreen) { document.webkitExitFullscreen() } } |
7、大小写转换
参数:
- str 待转换的字符串
- type 1-全大写 2-全小写 3-首字母大写
1 2 3 4 5 6 7 8 9 10 11 12 13 | export const turnCase = (str, type) => { switch (type) { case 1: return str.toUpperCase() case 2: return str.toLowerCase() case 3: //return str[0].toUpperCase() + str.substr(1).toLowerCase() // substr 已不推荐使用 return str[0].toUpperCase() + str.substring(1).toLowerCase() default : return str } } |
示例:
1 2 3 | turnCase( 'vue' , 1) // VUE turnCase( 'REACT' , 2) // react turnCase( 'vue' , 3) // Vue |
8、解析URL参数
1 2 3 4 5 6 7 8 | export const getSearchParams = () => { const searchPar = new URLSearchParams(window.location.search) const paramsObj = {} for (const [key, value] of searchPar.entries()) { paramsObj[key] = value } return paramsObj } |
示例:
1 2 | // 假设目前位于 https://****com/index?id=154513&age=18; getSearchParams(); // {id: "154513", age: "18"} |
9、判断手机是Andoird还是IOS
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 | /** * 1: ios * 2: android * 3: 其它 */ export const getOSType=() => { let u = navigator.userAgent, app = navigator.appVersion; let isAndroid = u.indexOf( 'Android' ) > -1 || u.indexOf( 'Linux' ) > -1; let isIOS = !!u.match(/\(i[^;]+;( U;)? CPU.+Mac OS X/); if (isIOS) { return 1; } if (isAndroid) { return 2; } return 3; } |
10、数组对象根据字段去重
参数:
- arr 要去重的数组
- key 根据去重的字段名
1 2 3 4 5 6 7 8 9 10 11 12 13 | export const uniqueArrayObject = (arr = [], key = 'id' ) => { if (arr.length === 0) return let list = [] const map = {} arr.forEach((item) => { if (!map[item[key]]) { map[item[key]] = item } }) list = Object.values(map) return list } |
示例:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 | const responseList = [ { id: 1, name: '树哥' }, { id: 2, name: '黄老爷' }, { id: 3, name: '张麻子' }, { id: 1, name: '黄老爷' }, { id: 2, name: '张麻子' }, { id: 3, name: '树哥' }, { id: 1, name: '树哥' }, { id: 2, name: '黄老爷' }, { id: 3, name: '张麻子' }, ] uniqueArrayObject(responseList, 'id' ) // [{ id: 1, name: '树哥' },{ id: 2, name: '黄老爷' },{ id: 3, name: '张麻子' }] |
11、滚动到页面顶部
1 2 3 4 5 6 7 | export const scrollToTop = () => { const height = document.documentElement.scrollTop || document.body.scrollTop; if (height > 0) { window.requestAnimationFrame(scrollToTop); window.scrollTo(0, height - height / 8); } } |
12、滚动到元素位置
1 2 3 4 5 | export const smoothScroll = element =>{ document.querySelector(element).scrollIntoView({ behavior: 'smooth' }); }; |
示例:
1 | smoothScroll( '#target' ); // 平滑滚动到 ID 为 target 的元素 |
13、uuid
1 2 3 4 5 6 | export const uuid = () => { const temp_url = URL.createObjectURL( new Blob()) const uuid = temp_url.toString() URL.revokeObjectURL(temp_url) //释放这个url return uuid.substring(uuid.lastIndexOf( '/' ) + 1) } |
示例:
1 | uuid() // c5cfffec-65bd-43bd-b656-29f36ccaaa42 |
14、金额格式化
参数:
- {number} number:要格式化的数字
- {number} decimals:保留几位小数
- {string} dec_point:小数点符号
- {string} thousands_sep:千分位符号
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 | export const moneyFormat = (number, decimals, dec_point, thousands_sep) => { number = (number + '' ).replace(/[^0-9+-Ee.]/g, '' ) const n = !isFinite(+number) ? 0 : +number const prec = !isFinite(+decimals) ? 2 : Math.abs(decimals) const sep = typeof thousands_sep === 'undefined' ? ',' : thousands_sep const dec = typeof dec_point === 'undefined' ? '.' : dec_point let s = '' const toFixedFix = function (n, prec) { const k = Math.pow(10, prec) return '' + Math.ceil(n * k) / k } s = (prec ? toFixedFix(n, prec) : '' + Math.round(n)).split( '.' ) const re = /(-?\d+)(\d{3})/ while (re.test(s[0])) { s[0] = s[0].replace(re, '$1' + sep + '$2' ) } if ((s[1] || '' ).length < prec) { s[1] = s[1] || '' s[1] += new Array(prec - s[1].length + 1).join( '0' ) } return s.join(dec) } |
示例:
1 2 | moneyFormat(10000000) // 10,000,000.00 moneyFormat(10000000, 3, '.' , '-' ) // 10-000-000.000 |
15、存储操作
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 | class MyCache { constructor(isLocal = true ) { this .storage = isLocal ? localStorage : sessionStorage } setItem(key, value) { if ( typeof (value) === 'object' ) value = JSON.stringify(value) this .storage.setItem(key, value) } getItem(key) { try { return JSON.parse( this .storage.getItem(key)) } catch (err) { return this .storage.getItem(key) } } removeItem(key) { this .storage.removeItem(key) } clear() { this .storage.clear() } key(index) { return this .storage.key(index) } length() { return this .storage.length } } const localCache = new MyCache() const sessionCache = new MyCache( false ) export { localCache, sessionCache } |
示例:
1 2 3 4 | localCache.getItem( 'user' ) sessionCache.setItem( 'name' , '树哥' ) sessionCache.getItem( 'token' ) localCache.clear() |
16、下载文件
参数:
- api 接口
- params 请求参数
- fileName 文件名
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 | const downloadFile = (api, params, fileName, type = 'get' ) => { axios({ method: type, url: api, responseType: 'blob' , params: params }).then((res) => { let str = res.headers[ 'content-disposition' ] if (!res || !str) { return } let suffix = '' // 截取文件名和文件类型 if (str.lastIndexOf( '.' )) { fileName ? '' : fileName = decodeURI(str.substring(str.indexOf( '=' ) + 1, str.lastIndexOf( '.' ))) suffix = str.substring(str.lastIndexOf( '.' ), str.length) } // 如果支持微软的文件下载方式(ie10+浏览器) if (window.navigator.msSaveBlob) { try { const blobObject = new Blob([res.data]); window.navigator.msSaveBlob(blobObject, fileName + suffix); } catch (e) { console.log(e); } } else { // 其他浏览器 let url = window.URL.createObjectURL(res.data) let link = document.createElement( 'a' ) link.style.display = 'none' link.href = url link.setAttribute( 'download' , fileName + suffix) document.body.appendChild(link) link.click() document.body.removeChild(link) window.URL.revokeObjectURL(link.href); } }). catch ((err) => { console.log(err.message); }) } |
使用:
1 | downloadFile( '/api/download' , {id}, '文件名' ) |
17、时间操作
关于时间操作,没必要自己再写一大串代码了,强烈推荐使用 day.js
1 | Day.js 是一个仅 2kb 大小的轻量级 JavaScript 时间日期处理库,下载、解析和执行的JavaScript更少,为代码留下更多的时间。 |
18、深拷贝
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 | export const clone = parent => { // 判断类型 const isType = (obj, type) => { if ( typeof obj !== "object" ) return false ; const typeString = Object.prototype.toString.call(obj); let flag; switch (type) { case "Array" : flag = typeString === "[object Array]" ; break ; case "Date" : flag = typeString === "[object Date]" ; break ; case "RegExp" : flag = typeString === "[object RegExp]" ; break ; default : flag = false ; } return flag; }; // 处理正则 const getRegExp = re => { var flags = "" ; if (re.global) flags += "g" ; if (re.ignoreCase) flags += "i" ; if (re.multiline) flags += "m" ; return flags; }; // 维护两个储存循环引用的数组 const parents = []; const children = []; const _clone = parent => { if (parent === null ) return null ; if ( typeof parent !== "object" ) return parent; let child, proto; if (isType(parent, "Array" )) { // 对数组做特殊处理 child = []; } else if (isType(parent, "RegExp" )) { // 对正则对象做特殊处理 child = new RegExp(parent.source, getRegExp(parent)); if (parent.lastIndex) child.lastIndex = parent.lastIndex; } else if (isType(parent, "Date" )) { // 对Date对象做特殊处理 child = new Date(parent.getTime()); } else { // 处理对象原型 proto = Object.getPrototypeOf(parent); // 利用Object.create切断原型链 child = Object.create(proto); } // 处理循环引用 const index = parents.indexOf(parent); if (index != -1) { // 如果父数组存在本对象,说明之前已经被引用过,直接返回此对象 return children[index]; } parents.push(parent); children.push(child); for ( let i in parent) { // 递归 child[i] = _clone(parent[i]); } return child; }; return _clone(parent); }; |
1 | 此方法存在一定局限性:一些特殊情况没有处理: 例如Buffer对象、Promise、Set、Map。 |
如果确实想要完备的深拷贝,推荐使用 lodash 中的 cloneDeep 方法。
19、模糊搜索
参数:
- list 原数组
- keyWord 查询的关键词
- attribute 数组需要检索属性
1 2 3 4 5 6 7 8 9 10 | export const fuzzyQuery = (list, keyWord, attribute = 'name' ) => { const reg = new RegExp(keyWord) const arr = [] for ( let i = 0; i < list.length; i++) { if (reg.test(list[i][attribute])) { arr.push(list[i]) } } return arr } |
示例:
1 2 3 4 5 6 7 8 9 10 | const list = [ { id: 1, name: '树哥' }, { id: 2, name: '黄老爷' }, { id: 3, name: '张麻子' }, { id: 4, name: '汤师爷' }, { id: 5, name: '胡万' }, { id: 6, name: '花姐' }, { id: 7, name: '小梅' } ] fuzzyQuery(list, '树' , 'name' ) // [{id: 1, name: '树哥'}] |
20、遍历树节点
1 2 3 4 5 6 7 8 | export const foreachTree = (data, callback, childrenName = 'children' ) => { for ( let i = 0; i < data.length; i++) { callback(data[i]) if (data[i][childrenName] && data[i][childrenName].length > 0) { foreachTree(data[i][childrenName], callback, childrenName) } } } |
示例:
假设我们要从树状结构数据中查找 id 为 9 的节点
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 | const treeData = [{ id: 1, label: '一级 1' , children: [{ id: 4, label: '二级 1-1' , children: [{ id: 9, label: '三级 1-1-1' }, { id: 10, label: '三级 1-1-2' }] }] }, { id: 2, label: '一级 2' , children: [{ id: 5, label: '二级 2-1' }, { id: 6, label: '二级 2-2' }] }, { id: 3, label: '一级 3' , children: [{ id: 7, label: '二级 3-1' }, { id: 8, label: '二级 3-2' }] }], let result foreachTree(data, (item) => { if (item.id === 9) { result = item } }) console.log( 'result' , result) // {id: 9,label: "三级 1-1-1"} |
【推荐】国内首个AI IDE,深度理解中文开发场景,立即下载体验Trae
【推荐】编程新体验,更懂你的AI,立即体验豆包MarsCode编程助手
【推荐】抖音旗下AI助手豆包,你的智能百科全书,全免费不限次数
【推荐】轻量又高性能的 SSH 工具 IShell:AI 加持,快人一步
· 全程不用写代码,我用AI程序员写了一个飞机大战
· MongoDB 8.0这个新功能碉堡了,比商业数据库还牛
· 记一次.NET内存居高不下排查解决与启示
· DeepSeek 开源周回顾「GitHub 热点速览」
· 白话解读 Dapr 1.15:你的「微服务管家」又秀新绝活了