javascript方法

136 阅读5分钟

new URLSearchParams(str)

处理url的查询字符串;
str必须传入确定的字符串:‘?not_token=1&stdsa=1233’
方法:
has(): 查询指定键名是否存在,返回一个Boolean值
get(): 获取指定搜索参数的第一个值
getAll(): 获取指定搜索参数的所有值,返回时一个数组
toString(): 返回搜索参数组成的字符串,可以直接使用在URL上
append(): 插入一个指定的健/值对作为新的搜索参数
set(): 设置一个搜索参数的新值,如果原来有多个值将删除其他所有的值
delete(): 从搜索参数列表删除指定的搜索参数及其对应的值
entries(): 返回一个iterator,允许遍历该对象中包含的所有健/值对。每一组键值对都说USVSString对象

判断数据类型的方法

function type (obj) {
    return Object.prototype.toString.call(obj).replace(/\[object\s|\]/g,'');
}
console.log(type([]))  //"Array"
console.log(type(1))  //"Number"

获取URL中的参数

//获取url中的参数
        function getUrlParam(name) {
            var reg = new RegExp("(^|&)" + name + "=([^&]*)(&|$)"); //构造一个含有目标参数的正则表达式对象
            var r = window.location.search.substr(1).match(reg);  //匹配目标参数
            if (r != null) return unescape(r[2]); return null; //返回参数值
        }

数组对象的几种去重方式

第一种:对象访问属性的方法
    let newArr = [];
    let obj = {};
    for (var i = 0; i < arr.length; i++) {
       if (!obj[arr[i].key]) {
         newArr.push(arr[i])
         obj[arr[i].key] = true
       }
    }
console.log(newArr);
第二种:Map()方法
let map = new Map();
for (let item of this.arr) {
    map.set(item.id, item);
 }
this.arr = [...map.values()];
console.log(this.arr)
第三种:reduce() 方法
const obj = {}
arr = arr.reduce((total, next) => {
  obj[next.key] ? '' : obj[next.key] = true && total.push(next)
  return total
}, [])
console.log(arr)
第四种:indexOf方法
function uniq(array) {
    var temp = []; //一个新的临时数组
    for (var i = 0; i < array.length; i++) {
        if (temp.indexOf(array[i]) == -1) {
            temp.push(array[i]);
        }
    }
    return temp;
}

验证身份证号的方法

function check(val){
    var reg=/^[1-9]\d{5}(19|20)\d{2}((0[1-9])|(1[0-2]))(([0-2][1-9])|(10|20|30|31))\d{3}[0-9Xx]$/;
     return reg.test(val);
}

获取图片的原始宽高

    function loadImageAsync(url) {
        return new Promise(function(resolve, reject) {
            var image = new Image();

            image.onload = function() {
                var obj = {
                    w: image.naturalWidth,
                    h: image.naturalHeight
                }
                resolve(obj);
            };

            image.onerror = function() {
                reject(new Error('Could not load image at ' + url));
            };
            image.src = url;
        });
    }

防抖和节流

type Timeout = number // browser
// type Timeout = NodeJS.Timeout // node

/**
 * 防抖:生成一个函数,它在被调用后会等待一段时间再执行。
 * 如果在等待期间再次调用,之前还未执行的调用会被取消。
 * @param fn 要防抖的函数
 * @param timeout 超时时间
 */
function debounce(fn: (...args: any[]) => any, timeout: number) {
    let time: Timeout = null
    return function _debounced(...args: any[]) {
        if (time !== null)
            { clearTimeout(time) }
        time = setTimeout(() => {
            fn(...args)
            time = null
        }, timeout)
    }
}

/**
 * 节流:生成一个函数,它在被调用后一段时间内再次被调用不起作用。
 * @param fn 要节流的函数
 * @param timeout 超时时间
 */
function throttle(fn: (...args: any[]) => any, timeout: number) {
    let time: Timeout = null
    return function _throttled(...args: any[]) {
        if (time === null) {
            fn(...args)
            time = setTimeout(() => time = null, timeout)
        }
    }
}

原生ajax方法get

 // 步骤一:创建异步对象
    var ajax = new XMLHttpRequest()
    // 步骤二: 设置请求的url参数,参数一是请求的类型,参数二是请求的url,可以带参数
    ajax.open('get', 'getStar.php?starName=' + name)
    // 步骤三: 发送请求
    ajax.send()
    // 步骤四:注册事件 onreadystatechange 状态改变就会调用
    ajax.onreadystatechange = function() {
        if (ajax.readystate == 4 && ajax.status == 200) {
            console.log(ajax.responseText)
        }
    }

post方法

    // 创建异步对象
    var ajax = new XMLHttpRequest()
    // post请求一定要添加请求头才行不然会报错
    ajax.setRequestHeader('content-type', 'application/x-www-form-urlencoded')
    // 设置请求的类型与参数
    ajax.open('post', '02.post.php')
    // 发送请求
    ajax.send('请求参数')
    // 注册事件
    ajax.onreadystatechange = function () {
        if (ajax.readystate == 4 && ajax.status == 200) {
            console.log(ajax.responseText)
        }
    }

手写new

function newCopy(){
    // 创建空对象
    let obj = new Object()
    // 声明一个类
    let constructor = Array.from(arguments).shift()
    // 空对象的__proto__指向类的原型对象
    obj.__proto__ = constructor.prototype
    // 执行上下文
    let result = constructor.call(obj, ...Array.from(arguments).slice(1))
    // 类的this指向执行对象
    return typeof result === 'object' ? result : obj
}

手写call

Function.prototype.newCall = function(content){
    // 1、创建传参的属性
    content = typeof content === 'object' ? content : window
    content.data = this
    // 2、执行
    let args = [...arguments].slice(1)
    let result = content.data(...args)
    // 删除自定义的属性
    delete content.data
    return result
}

手写apply

Function.prototype.newApply = function(content){
    console.log(content)
    content = typeof content === 'object' ? content : window
    content.data = this
    let args = [...arguments][1]
    let result = content.data(...args)
    delete content.data
    return result
}

手写bind

Function.prototype.newBind = function(content){
    console.log(this)
    content = typeof content === 'object' ? content : window
    let self = this
    let args = [...arguments].slice(1)
    let fn = new Function()
    let fBound = function(){
        return self.call(this instanceof fBound ? this : content, ...[...args, ...arguments])
    }
    fn.prototype = self.prototype
    fBound.prototype = new fn()
    return fBound
}

深拷贝

function deepCopy(obj) {
    let objClone = Array.isArray(obj) ? [] : {}
    if (obj && typeof obj === 'object') {
        for (key in obj) {
            if (obj.hasOwnProperty(key)) {
                if (obj[key] && typeof obj[key] === 'object') {
                    objClone[key] = deepCopy(obj[key])
                } else {
                    objClone[key] = obj[key]
                }
            }
        }
    }
    return objClone
}

封装ajax

 function ajaxData (url, methed, data, success) {
    var ajax = new XMLHttpRequest()
    if (methed == 'get') {
        var list = ''
        if (data) {
            list = url + '?' + data
        } else {
            list = url
        }
        ajax.open(methed, list)
        // ajax.setRequestHeader('authorization', 'Bearer TGT-11177-jowV0MHO1paqeRYIb5y5h0UTKz22DhQmKFJttdURtZAZtcCb3R-SIAM')
    } else {
        ajax.setRequestHeader('content-type', 'application/x-www-form-urlencoded')
        ajax.open(methed, url)
        ajax.send(data)
    }
    ajax.onreadystatechange = function () {
        if (ajax.readystate == 4 && ajax.status == 200) {
            console.log(ajax.responseText)
            success(ajax.responseText)
        }
    }
}
ajaxData('https://t-portal.wanyol.com/api/v2/userInfo/selectReaders', 'get', 'readerType=1&search=mao', function(res) {
    console.log(res, '===')
})

删除url中某个参数,并跳转

function funcUrlDel (name) {
  const loca = window.location
  const pathName = loca.pathname
  const query = loca.search.substr(1)
  if (query.indexOf(name) > -1) {
    const obj = {}
    const arr = query.split('&')
    for (let i = 0; i < arr.length; i++) {
      arr[i] = arr[i].split('=')
      obj[arr[i][0]] = arr[i][1]
    }
    delete obj[name]
    let url = JSON.stringify(obj).replace(/["{}]/g, '').replace(/:/g, '=').replace(/,/g, '&')
    // 如果还有参数,则使用?拼接回去原来的url
    if (url) {
      url = (pathName + '?' + url)
    }
    return url || pathName
  }
}
例如:funcUrlDel('token')

path

function isExternal (path) {
  return /^(https?:|mailto:|tel:)/.test(path)
}

url

function validURL (url) {
  const reg = /^(https?|ftp):\/\/([a-zA-Z0-9.-]+(:[a-zA-Z0-9.&%$-]+)*@)*((25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9][0-9]?)(\.(25[0-5]|2[0-4][0-9]|1[0-9]{2}|[1-9]?[0-9])){3}|([a-zA-Z0-9-]+\.)*[a-zA-Z0-9-]+\.(com|edu|gov|int|mil|net|org|biz|arpa|info|name|pro|aero|coop|museum|[a-zA-Z]{2}))(:[0-9]+)*(\/($|[a-zA-Z0-9.,?'\\+&%$#=~_-]+))*$/
  return reg.test(url)
}
function getQueryObject (url) {
  url = url == null ? window.location.href : url
  const search = url.substring(url.lastIndexOf('?') + 1)
  const obj = {}
  const reg = /([^?&=]+)=([^?&=]*)/g
  search.replace(reg, (rs, $1, $2) => {
    const name = decodeURIComponent($1)
    let val = decodeURIComponent($2)
    val = String(val)
    obj[name] = val
    return rs
  })
  return obj
}

str

function validLowerCase (str) {
  const reg = /^[a-z]+$/
  return reg.test(str)
}
function validUpperCase (str) {
  const reg = /^[A-Z]+$/
  return reg.test(str)
}
function validAlphabets (str) {
  const reg = /^[A-Za-z]+$/
  return reg.test(str)
}

email

unction validEmail (email) {
  const reg = /^(([^<>()\[\]\\.,;:\s@"]+(\.[^<>()\[\]\\.,;:\s@"]+)*)|(".+"))@((\[[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\.[0-9]{1,3}\])|(([a-zA-Z\-0-9]+\.)+[a-zA-Z]{2,}))$/
  return reg.test(email)
}

arg

function isArray (arg) {
  if (typeof Array.isArray === 'undefined') {
    return Object.prototype.toString.call(arg) === '[object Array]'
  }
  return Array.isArray(arg)
}

设置时间

// 对Date的扩展,将 Date 转化为指定格式的String
// 月(M)、日(d)、小时(h)、分(m)、秒(s)、季度(q) 可以用 1-2 个占位符,
// 年(y)可以用 1-4 个占位符,毫秒(S)只能用 1 个占位符(是 1-3 位的数字)
// (new Date()).Format("yyyy-MM-dd hh:mm:ss.S") ==> 2006-07-02 08:09:04.423
// (new Date()).Format("yyyy-M-d h:m:s.S")      ==> 2006-7-2 8:9:4.18
Date.prototype.Format = function (fmt) {
  var o = {
    'M+': this.getMonth() + 1, // 月份
    'd+': this.getDate(), // 日
    'h+': this.getHours(), // 小时
    'm+': this.getMinutes(), // 分
    's+': this.getSeconds(), // 秒
    'q+': Math.floor((this.getMonth() + 3) / 3) // 季度
    // 'S': this.getMilliseconds() // 毫秒
  }
  if (/(y+)/.test(fmt)) { fmt = fmt.replace(RegExp.$1, (this.getFullYear() + '').substr(4 - RegExp.$1.length)) }
  for (var k in o) {
    if (new RegExp('(' + k + ')').test(fmt)) { fmt = fmt.replace(RegExp.$1, (RegExp.$1.length === 1) ? (o[k]) : (('00' + o[k]).substr(('' + o[k]).length))) }
  }
  return fmt
}
// 转换时间格式
export function formatTimeToStr (times, pattern) {
  let d = new Date(times).Format('yyyy-MM-dd hh:mm:ss')
  if (pattern) {
    d = new Date(times).Format(pattern)
  }
  return d.toLocaleString()
}
// 设置默认时间默认为时分秒type 0: 00:00:00 type 1: 23:59:59
export function changeTime (date, type = 0) {
  const d = new Date(date)
  if (type === 1) {
    d.setHours(23)
    d.setSeconds(59)
    d.setMinutes(59)
  } else {
    d.setHours(0)
    d.setSeconds(0)
    d.setMinutes(0)
  }
  return d
}
// 获取距离当前时间,后几天。默认7天
export function getDistanceTime (day = 7, data = new Date()) {
  return data.getTime() + 3600 * 1000 * 24 * (Number(day) - 1)
}
// 设置时间控件默认不能选中的时间,默认今天, day
export function pickerOptions (day = -1) {
  return {
    disabledDate (time) {
      return time.getTime() < Date.now() + 3600 * 1000 * 24 * day
    }
  }
}
// 计算两个日期相差的天数 yyyy-MM-dd
export function getDaysBetween (dateString1, dateString2 = formatTimeToStr(new Date(), 'yyyy-MM-dd')) {
  const startDate = Date.parse(dateString1)
  const endDate = Date.parse(dateString2)
  const days = (endDate - startDate) / (1 * 24 * 60 * 60 * 1000)
  return -days
}

文件下载

function getDownload (data, matched) {
  let fileName
  if (matched && matched[2]) {
    if (matched[1] !== '') {
      try {
        matched[1] = decodeURI(matched[1])
      } catch (e) {}
    } else {
      matched[1] = '默认'
    }
    fileName = matched[1] + '.' + matched[2]
  } else {
    fileName = '导出文件'
  }
  const blob = new Blob([data])
  if (window.navigator.msSaveBlob) {
    try {
      window.navigator.msSaveBlob(blob, fileName)
    } catch (e) {
      console.log(e)
    }
  } else {
    let downloadElement = document.createElement('a')
    let href = window.URL.createObjectURL(blob)
    downloadElement.href = href
    downloadElement.download = fileName
    document.body.appendChild(downloadElement)
    downloadElement.click()
    document.body.removeChild(downloadElement)
    window.URL.revokeObjectURL(href)
  }
}

时间处理

function parseTime (time, cFormat) {
  if (arguments.length === 0) {
    return null
  }
  const format = cFormat || '{y}-{m}-{d} {h}:{i}:{s}'
  let date
  if (typeof time === 'object') {
    date = time
  } else {
    if ((typeof time === 'string')) {
      if ((/^[0-9]+$/.test(time))) {
        // support "1548221490638"
        time = parseInt(time)
      } else {
        // support safari
        // https://stackoverflow.com/questions/4310953/invalid-date-in-safari
        time = time.replace(new RegExp(/-/gm), '/')
      }
    }

    if ((typeof time === 'number') && (time.toString().length === 10)) {
      time = time * 1000
    }
    date = new Date(time)
  }
  const formatObj = {
    y: date.getFullYear(),
    m: date.getMonth() + 1,
    d: date.getDate(),
    h: date.getHours(),
    i: date.getMinutes(),
    s: date.getSeconds(),
    a: date.getDay()
  }
  const time_str = format.replace(/{([ymdhisa])+}/g, (result, key) => {
    const value = formatObj[key]
    // Note: getDay() returns 0 on Sunday
    if (key === 'a') { return ['日', '一', '二', '三', '四', '五', '六'][value] }
    return value.toString().padStart(2, '0')
  })
  return time_str
}
function formatTime (time, option) {
  if (('' + time).length === 10) {
    time = parseInt(time) * 1000
  } else {
    time = +time
  }
  const d = new Date(time)
  const now = Date.now()

  const diff = (now - d) / 1000

  if (diff < 30) {
    return '刚刚'
  } else if (diff < 3600) {
    // less 1 hour
    return Math.ceil(diff / 60) + '分钟前'
  } else if (diff < 3600 * 24) {
    return Math.ceil(diff / 3600) + '小时前'
  } else if (diff < 3600 * 24 * 2) {
    return '1天前'
  }
  if (option) {
    return parseTime(time, option)
  } else {
    return (
      d.getMonth() +
      1 +
      '月' +
      d.getDate() +
      '日' +
      d.getHours() +
      '时' +
      d.getMinutes() +
      '分'
    )
  }
}
function handleSecondTimeParams (params, timeData, startTime, endTime) {
  let copyParams = deepCopy(params)
  // 开始时间和结束时间对应赋值
  if (copyParams[timeData] && copyParams[timeData].length === 2) {
    copyParams[startTime] = copyParams[timeData][0]
    copyParams[endTime] = copyParams[timeData][1]
    // 重置筛选项
  } else if (copyParams[timeData] && copyParams[timeData].length < 2) {
    copyParams[startTime] = ''
    copyParams[endTime] = ''
  }
  delete copyParams[timeData]
  return copyParams
}