前端api笔记整理合集

    • 获取高度以及其他属性
       getBoundingClientRect()   offsetLeft 
       window.getComputedStyle(test);   currentStyle  getPropertyValue("background-color")  oStyle.getAttribute("backgroundColor"));
       document.createTextNode("CLICK ME");
       
      var test = document.querySelector('.test')
      var oStyle = test.currentStyle? test.currentStyle : window.getComputedStyle(test, null);
      console.log(oStyle.height)
      // console.log(oStyle.getPropertyValue('background-color'))
      if (oStyle.getPropertyValue) {
        console.log("getPropertyValue下背景色:" + oStyle.getPropertyValue("background-color"));
      } else {
        console.log("getAttribute下背景色:" + oStyle.getAttribute("backgroundColor"));
      }
    
    • new 的时候发生了什么?
    var obj = new Base();
    var obj  = {};
    obj.__proto__ = Base.prototype;
    Base.call(obj);
    
    • 单例模式私有变量,私有方法
    var single=function (argument) {
        var privateVar=10;
        function privateFun () {
            //私有方法函数
        }
        return {
            publicProerty:true,
            //返回的共有方法可访问私有变量
            publicMethod:function () {
                privateVar++;
                return privateFun()
            }
        }
    }
    

    闭包的私有变量

    function Foo(){
        var n=10;
        this.returnN=function(){
            return n;
        };
    };
    var newfoo=new Foo();
    console.log(newfoo.returnN())//10
    

    es6的私有变量

    class Foo {
      #a;
      #b;
      #sum() { return #a + #b; }
      printSum() { console.log(#sum()); }
      constructor(a, b) { #a = a; #b = b; }
    }
    

    判断是否是数组

    Array.isArray([])
    [] instanceOf Array
    ({}).toString.call([]) === '[object Array]'
    [].constructor === Array
    

    object.create()

    object.create = function cc(o){
    var F = function(){}
    F.prototype = o;
    return new F();
    }
    a2 = object.create(a1) 
    a2.__proto__ = a1
    

    js 判断是否是继承链上啊

    function C(){} 
    function D(){} 
    var o = new C();
    o instanceof C;
    instanceof  //不能判断基本类型
    null undefined  constructor //报错
    Object.prototype.toString.call(null); //万金油判断类型
    
    • documnet.ready

       事件的触发,表示文档结构已经加载完成(不包含图片等非文字媒体文件)。
      
    • window.onload

      事件的触发,表示页面包含图片等文件在内的所有元素都加载完成。
      
    • AMD 和 CMD区别

    1AMD推崇依赖前置,在定义模块的时候就要声明其依赖的模块 
    2CMD推崇就近依赖,只有在用到某个模块的时候再去require
    
    word-break:break-all;
    word-wrap:break-word;
    
    线程是CPU调用(执行任务)的最小单位。
    进程是CPU分配资源和调度的单位。
    
    • Boolean(value)
    把给定的值转换成Boolean型。 
    当要转换的值是至少有一个字符的字符串、非0数字或对象时,Boolean()函数将返回true。如果该值是空字符串、数字0、undefined或null,它将返回false
    • bind 方法

      将第一个参数设置为函数执行的上下文,其他参数依次传递给调用方法(函数的主体本身不执行,可以看成是延迟执行),并动态创建返回一个新的函数, 这符合柯里化特点。

      var foo = {x: 888};
      var bar = function () {
          console.log(this.x);
      }.bind(foo);               // 绑定
      bar();                     // 888
      
    • bind的原生实现

    Function.prototype.testBind = function(that){
            var _this = this,
                slice = Array.prototype.slice,
                args = slice.apply(arguments,[1]),
                fNOP = function () {},
                bound = function(){
                    //这里的this指的是调用时候的环境
                    return _this.apply(this instanceof  fNOP ? this : that||window,
                        args.concat(Array.prototype.slice.apply(arguments,[0]))
                    )
                }    
            fNOP.prototype = _this.prototype;
        
            bound.prototype = new fNOP();
        
            return bound;
        }
    

    js模块

    //CommonJS
    exports.add = function(a, b) {
      return a + b;
    }
    var math = require('math');
    math.add(2, 3); // 5
    //缺点 同步加载假死
    
    • AMD
    // RequireJS 浏览器端模块化开发的目的
    // AMD ”Asynchronous Module Definition”
    // math.js
    define(function() {
      var add = function(x, y) {
        return x + y;
      }
    
      return  {
        add: add
      }
    })
    
    require([module], callback);
    require(['math'], function(math) {
      math.add(2, 3);
    })
    //特点 说AMD是依赖前置的
    //代码在一旦运行到此处,能立即知晓依赖。
    //而无需遍历整个函数体找到它的依赖,
    //因此性能有所提升,缺点就是开发者必须显式得指明依赖——
    //这会使得开发工作量变大,
    //比如:当你写到函数体内部几百上千行的时候
    //,忽然发现需要增加一个依赖,你不得不回到函数顶端
    //来将这个依赖添加进数组。
    
    • CMD
    // Seajs
    define(function(require, exports, module) {
      var a = require('./a');
      a.doSomething();
      var b = require('./b');
      b.doSomething();
    })
    //特点 依赖就近
    // 这是一种牺牲性能来换取更多开发便利的方法。
    
    • UMD 兼容

    • ES6

    // 导出变量
    export var a = 1;
    export var b = 2;
    export var c = 3;
    export default c;
    // 导出变量
    var a = 1;
    var b = 2;
    var c = 3;
    export {a, b, c}
    // 导出函数
    function foo(){}
    function bar(){}
    export {foo, bar as bar2}
    
    import * as m from './foo';
    
    • filter去重
    [1,2,3,1,'a',1,'a'].filter(function(ele,index,array){
        return index===array.indexOf(ele)
    })
    

    原生js ajax

    //步骤一:创建异步对象
    var ajax = new XMLHttpRequest();
    //步骤二:设置请求的url参数,参数一是请求的类型,参数二是请求的url,可以带参数,动态的传递参数starName到服务端
    ajax.open('get','getStar.php?starName='+name);
    //步骤三:发送请求
    ajax.send();
    //步骤四:注册事件 onreadystatechange 状态改变就会调用
    ajax.onreadystatechange = function () {
       if (ajax.readyState==4 &&ajax.status==200) {
        //步骤五 如果能够进到这个判断 说明 数据 完美的回来了,并且请求的页面是存在的
        console.log(xml.responseText);//输入相应的内容
        }
    }
    //post
    var xhr = new XMLHttpRequest();
    //设置请求的类型及url
    //post请求一定要添加请求头才行不然会报错
    xhr.setRequestHeader("Content-type","application/x-www-form-urlencoded");
     xhr.open('post', '02.post.php' );
    //发送请求
    xhr.send('name=fox&age=18');
    xhr.onreadystatechange = function () {
        // 这步为判断服务器是否正确响应
      if (xhr.readyState == 4 && xhr.status == 200) {
        console.log(xhr.responseText);
      } 
    };
    // readyState的几种状态:
    // 0:初始化,XMLHttpRequest对象还没有完成初始化
    // 1:载入,XMLHttpRequest对象开始发送请求
    // 2:载入完成,XMLHttpRequest对象的请求发送完成,已收到全部响应内容但尚未解析
    // 3:解析,XMLHttpRequest对象开始解析服务器的响应内容
    // 4:完成,XMLHttpRequest对象读取服务器响应结束
    
    IE浏览器
    xmlHttp=new ActiveXObject("Msxml2.XMLHTTP");
    
    • 函数防抖
    // 防抖
    var canRun = true;
    document.getElementById("throttle").onscroll = function(){
        if(!canRun){
            // 判断是否已空闲,如果在执行中,则直接return
            return;
        }
    
        canRun = false;
        setTimeout(function(){
            console.log("函数节流");
            canRun = true;
        }, 300);
    };
    // 将若干个函数调用合成一次,并在给定时间过去之后仅被调用一次。
    
    • 节流
    // 节流函数允许一个函数在规定的时间内只执行一次。
    // 它和防抖动最大的区别就是,节流函数不管事件触发有多频繁,都会保证在规定时间内一定会执行一次真正的事件处理函数。
    var throttle = function(func,delay){
        var prev = Date.now();
        return function(){
            var context = this;
            var args = arguments;
            var now = Date.now();
            if(now-prev>=delay){
                func.apply(context,args);
                prev = Date.now();
            }
        }
    }
    

    HTTP1.0 和 HTTP2.0

    //HTTP1.0与HTTP 1.1的主要区别 
    长连接
    节约带宽
    HOST域
    管道机制
    http1.1所有的数据通信是按次序进行的
    // http1.0的缺陷
    每个请求都需单独建立连接(keep-alive能解决部分问题单不能交叉推送)
    每个请求和响应都需要完整的头信息
    
    
    // http2的优势
    多路复用(SDPY协议是HTTP2的基础,它的核心思想是多路复用,仅使用一个连接链传输一个网页中的众多资源:)
    压缩头信息(根据资源请求的特性和优先级,调整这些资源请求的优先级。)
    请求划分优先级
    支持服务器端主动推送 (一方面使用gzip或compress压缩后再发送;另一方面,客户端和服务器
    时维护一张头信息表,所有字段都会存入这个表,生成一个索引号,以后就不发送同样字段了,只发送索引号)
    而HTTP2的基本协议单位为二进制帧流
    SDPY必须建立在SSL协议之上  必须使用https
    
    //Connection: keep-alive。
    TCP连接默认不关闭
    
    • TCP与UDP基本区别
      1.基于连接与无连接
      2.TCP要求系统资源较多,UDP较少; 
      3.UDP程序结构较简单 
      4.流模式(TCP)与数据报模式(UDP); 
      5.TCP保证数据正确性,UDP可能丢包 
      6.TCP保证数据顺序,UDP不保证 
      
    UDP应用场景:
      1.面向数据报方式
      2.网络数据大多为短消息 
      3.拥有大量Client
      4.对数据安全性无特殊要求
      5.网络负担非常重,但对响应速度要求高
    
    dns 预取技术 tcp预连接
    UI线程是brower线程中的主线程
    主线程的目的是保持用户界面的高度相应
    

    webpack

    webpack 的初衷,require everything, bundle everything.
    Gulp 的定位是 Task Runner, 就是用来跑一个一个任务的。
    

    数组去重

    // ES6
    function unique (arr) {
      const seen = new Map()
      return arr.filter((a) => !seen.has(a) && seen.set(a, 1))
    }
    // or
    function unique (arr) {
      return Array.from(new Set(arr))
    }
    // 普通
    
    function unique(array){ 
        var n = []; //一个新的临时数组 
        
        for(var i = 0; i < array.length; i++){ 
            if (n.indexOf(array[i]) == -1) n.push(array[i]); 
        } 
        return n; 
    }
    

    原型

    function A(){};  
    var a = new A();
    console.log(A.prototype.constructor==A)
    console.log(a.constructor == A)
    console.log(a.__proto__ == A.prototype)
    console.log(A.__proto__ == Function.prototype)
    
    reduce
    arr.reduce((a,b)=>a+b)
    // 求和
    console.log(eval(arr.join("+")))
    // 求和
    arr = [1,2,3,4,5]
    cc = arr.reduce(sum,0)
    function sum(a,b,index,arr){
      console.log(a,b,index,arr)
      return a+b
    }
    console.log(cc)
    // 1 2 1 [1, 2, 3, 4, 5]
    // 3 3 2 [1, 2, 3, 4, 5]
    // 6 4 3 [1, 2, 3, 4, 5]
    // 10 5 4 [1, 2, 3, 4, 5]
    // 15
    
    sort
    arr.sort((a,b)=>a-b)
    
    // 由小到大的排序
    var arr = [4,3,6,5,7,2,1];
    arr.sort();
    arr.sort(function(a,b){
        return a-b;
    });
    console.log(arr);
    //输出结果 [1, 2, 3, 4, 5, 6, 7]
    // sort的运算结果是sort后然后比较大小 如果a-b<1 那么 不动如果大于1 那么交换顺序 
    // a-b是从小到大
    // b-a是从大到小
    
    冒泡排序
    arr=[6,2,14,15,12,47,26,38,1,3,9,5,4,8,54,23,16,17,18,19,20,21]
    
    for(let i=0; i<arr.length ; i++){
      for(let j=0;j<arr.length-i-1; j++){
        if(arr[j] > arr[j+1]){
          [ arr[j], arr[j+1] ] = [ arr[j+1] , arr[j] ]
        }
      }
    }
    
    Math.max
    arr = [1,2,3]
    Math.max(...arr)//3
    Math.max.apply(null,arr)//3
    
    ##### 判断是否是回文
    var gg = 'abccba'
    function palindrome(text){
        return text.split('').reverse().join('') === text?'是回文':'不是回文'
    }
    console.log(palindrome(gg))
    

    js翻转字符串

    function reverseString(str) {  
        return (str === '') ? '' : reverseString(str.substr(1)) + str.charAt(0);  
    } 
    function reverseString(str){
        return str.split('').reverse().join('');
    }
    

    正则匹配数字

    var test='abc345efgabcab'; 
    uu = test.replace(/(\d)/g,'[$1]'); 
    console.log(uu) // abc[3][4][5]efgabcab
    

    递归算法

    //二分查找
    function binSearch(target, arr, start, end) {
      var start = start || 0; // 允许从什么位置开始,下标
      var end = end || arr.length - 1; // 什么位置结束,下标
      start >= end ? -1 : ''; // 没有找到,直接返回-1
      var mid = Math.floor((start + end) / 2); // 中位下标
      if (target == arr[mid]) {
        return mid; // 找到直接返回下标
      } else if (target > arr[mid]) {
        //目标值若是大于中位值,则下标往前走一位
        return binSearch(target, arr, start, mid - 1);
      } else {
        //若是目标值小于中位值,则下标往后退一位
        return binSearch(target, arr, mid + 1, end);
      }
    }
    

    js深拷贝

    function deepClone(obj){
        var newObj = obj.constructor === Array ? []:{};
        if(typeof obj !== 'object'){
            return
        }else{
            for(var i in obj){
                if(obj.hasOwnProperty(i)){
                    newObj[i] = typeof obj[i] === 'object'?deepClone(obj[i]):obj[i];
                }
            }
        }
        return newObj
    }
    

    自定义事件

      //自定义事件
      var box = document.getElementById('box')
      // var evt = new Event("look", {"bubbles":true, "cancelable":false});
      // box.addEventListener('look',function (argument) {
      //   console.log('我是look监听事件')
      // })
      var event = new CustomEvent("cat", {"detail":{"hazcheeseburger":true}})
      box.addEventListener("cat", function(e) { console.log(e.detail) })
      // box.dispatchEvent(event)
      setTimeout(()=>{
        box.dispatchEvent(event);
      },1000)
    

    相对窗口 offsetTop
    相对视口 getBoundingClientRect() dom

    map和foreach的区别

    arr = [1,2,3,4,5]
    arr.forEach(function(element, index, array) {
      console.log(element, index)
    });
    cc = arr.map(function(element, index, array) {
      return element*2
    })
    var numbers = [1, 4, 9];
    var roots = numbers.map(Math.sqrt);  [1, 2, 3];
    console.log(cc) // [2, 4, 6, 8, 10]
    // Map和forEach的区别
    // 1、map速度比foreach快
    // 2、map会返回一个新数组,不对原数组产生影响,foreach不会产生新数组,foreach返回undefined
    // 3、map因为返回数组所以可以链式操作,foreach不能
    // 4, map里可以用return ,而foreach里用return不起作用,foreach不能用break,会直接报错
    

    正则匹配金额

      function toS(num){
            let reg =/\B(?=(\d{3})+\b)/g; //B表示匹配非单词边界的元字符,而/b表示匹配单词边界
            console.log(num.replace(reg,","))
        }
    
        toS(10000000000+"");//1,000,000,000
    

    js == 比较

    如果一个值是Object,另一个是number或者string,会把Object利用 valueOf()或者toString()转换成原始类型再进行比较
    在数值运算里,会优先调用valueOf(),如a + b;
    在字符串运算里,会优先调用toString(),如alert(c)。
    []+[] toString()
    ""
    []-[]  先转成valueOf 然后转成number
    0 
    {}+{}  toString()
    "[object Object][object Object]"
    {}-{}  先转成valueOf 然后转成number
    NaN
    {}==0  先转成valueOf 然后转成number
    console.log([0,1]=='0,1')
    先调用valueOf  然后调用toString
    

    https://www.cnblogs.com/huaan011/p/6634349.html

    标记清除 树的遍历

    事件委托

    <ul id="ul1">
        <li>111</li>
        <li>222</li>
        <li>333</li>
        <li>444</li>
      </ul>
      <script>
        window.onload = function(){
          var oUl = document.getElementById("ul1");
          oUl.onclick = function(ev){
               //父元素
              console.log(ev.currentTarget);
            var ev = ev || window.event;
            var target = ev.target || ev.srcElement;
            if(target.nodeName.toLowerCase() == 'li'){
                 console.log(target.innerHTML);
            }
          }
        }
      </script> 
    

    JS如何实现多重继承?

    js转化abcDefGhi,返回:abc_def_ghi
    function tranvert(str){
        reg = /([A-Z])+/g;
        return str.replace(reg,'_$1').toLocaleLowerCase()
    }
    console.log(tranvert('getYourName'))
    

    二分法

    // 循环二分法
    function bfind(array,target){
      let left = 0
      let right = array.length -1
      while(left <= right){
        mid = Math.floor((left + right)/2);
        if(target > array[mid]){
          left = mid+1;
          continue;
        }else if(target == array[mid]){
          return mid;
        }else {
          right = mid-1;
          continue;
        }
      }
    }
    
    //递归二分法
    function bfind(array,target,left,right){
      var mid = Math.floor((left + right)/2);
      if(target > array[mid]){
        return bfind(array,target,mid+1,right)
      }else if(target < array[mid]){
        return bfind(array,target,left,mid-1)
      }else {
        return mid
      }
    }
    console.log(bfind([1,2,3,4,5,6],4,0,5))
    
    Last Updated: 10/26/2018, 3:27:14 PM