美文网首页程序员简友广场
关于vue源码工具函数系列总结(持续更新)

关于vue源码工具函数系列总结(持续更新)

作者: Splendid飞羽 | 来源:发表于2020-08-09 23:45 被阅读0次
    工具函数封装系列(v2.6.11)
    These helpers produce better VM code in JS engines due to their
    explicitness and function inlining.

    判断各种类型

    var _toString = Object.prototype.toString;
    
    function toRawType(value) {
        return _toString.call(value).slice(8, -1)
    }
    
    //   eg:
    //   toRawType(123)
    //   "Number"
    //   toRawType('assasa')
    //   "String"
    //   toRawType({a:1})
    //   "Object"
    //   toRawType([1,2,3])
    //   "Array"
    

    序列化:

    function toString(val) {
        return val == null
            ? ''
            : typeof val === 'object'
                ? JSON.stringify(val, null, 2)
                : String(val)
    }
    

    群组判断(重要)

    function makeMap(
        str,
        expectsLowerCase
    ) {
        var map = Object.create(null);
        var list = str.split(',');
        for (var i = 0; i < list.length; i++) {
            map[list[i]] = true;
        }
        return expectsLowerCase
            ? function (val) { return map[val.toLowerCase()]; }
            : function (val) { return map[val]; }
    }
    
    //eg1:是否是html标签  svg标签
    
    
    var isHTMLTag = makeMap(
        'html,body,base,head,link,meta,style,title,' +
        'address,article,aside,footer,header,h1,h2,h3,h4,h5,h6,hgroup,nav,section,' +
        'div,dd,dl,dt,figcaption,figure,picture,hr,img,li,main,ol,p,pre,ul,' +
        'a,b,abbr,bdi,bdo,br,cite,code,data,dfn,em,i,kbd,mark,q,rp,rt,rtc,ruby,' +
        's,samp,small,span,strong,sub,sup,time,u,var,wbr,area,audio,map,track,video,' +
        'embed,object,param,source,canvas,script,noscript,del,ins,' +
        'caption,col,colgroup,table,thead,tbody,td,th,tr,' +
        'button,datalist,fieldset,form,input,label,legend,meter,optgroup,option,' +
        'output,progress,select,textarea,' +
        'details,dialog,menu,menuitem,summary,' +
        'content,element,shadow,template,blockquote,iframe,tfoot'
    );
    
    var isSVG = makeMap(
        'svg,animate,circle,clippath,cursor,defs,desc,ellipse,filter,font-face,' +
        'foreignObject,g,glyph,image,line,marker,mask,missing-glyph,path,pattern,' +
        'polygon,polyline,rect,switch,symbol,text,textpath,tspan,use,view',
        true
    );
    
    var isReservedTag = function (tag) {
        return isHTMLTag(tag) || isSVG(tag)
    };
    
    
    
    //eg2:这里定义了必须使用属性的判断的函数:  value这个属性的tag有:input,textarea,option,select,progress  这些标签    归属的判断
    
    
    var acceptValue = makeMap('input,textarea,option,select,progress');
    var mustUseProp = function (tag, type, attr) {
        return (
            (attr === 'value' && acceptValue(tag)) && type !== 'button' ||
            (attr === 'selected' && tag === 'option') ||
            (attr === 'checked' && tag === 'input') ||
            (attr === 'muted' && tag === 'video')
        )
    };
    
    
    
    //eg3:布尔值的属性的词
    var isBooleanAttr = makeMap(
        'allowfullscreen,async,autofocus,autoplay,checked,compact,controls,declare,' +
        'default,defaultchecked,defaultmuted,defaultselected,defer,disabled,' +
        'enabled,formnovalidate,hidden,indeterminate,inert,ismap,itemscope,loop,multiple,' +
        'muted,nohref,noresize,noshade,novalidate,nowrap,open,pauseonexit,readonly,' +
        'required,reversed,scoped,seamless,selected,sortable,translate,' +
        'truespeed,typemustmatch,visible'
    );
    

    判断字符类型

    function getPathCharType(ch) {
       if (ch === undefined) {
           return 'eof';
       }
    
       var code = ch.charCodeAt(0);
    
       switch (code) {
           case 0x5B: // [
           case 0x5D: // ]
           case 0x2E: // .
           case 0x22: // "
           case 0x27: // '
           case 0x30:
               // 0
               return ch;
    
           case 0x5F: // _
           case 0x24:
               // $
               return 'ident';
    
           case 0x20: // Space
           case 0x09: // Tab
           case 0x0A: // Newline
           case 0x0D: // Return
           case 0xA0: // No-break space
           case 0xFEFF: // Byte Order Mark
           case 0x2028: // Line Separator
           case 0x2029:
               // Paragraph Separator
               return 'ws';
       }
    
       // a-z, A-Z
       if (code >= 0x61 && code <= 0x7A || code >= 0x41 && code <= 0x5A) {
           return 'ident';
       }
    
       // 1-9
       if (code >= 0x31 && code <= 0x39) {
           return 'number';
       }
    
       return 'else';
    }
    

    hasOwnProperty 的封装

    var hasOwnProperty = Object.prototype.hasOwnProperty;
    function hasOwn(obj, key) {
        return hasOwnProperty.call(obj, key)
    }
    
    hasOwn({ aaa: 1 }, 'aaa') //true
    

    函数缓存

    function cached(fn) {
        var cache = Object.create(null);
        return (function cachedFn(str) {
            var hit = cache[str];
            return hit || (cache[str] = fn(str))
        })
    }
    

    转驼峰实现 ---Camelize a hyphen-delimited string.

    var camelizeRE = /-(\w)/g;
    var camelize = cached(function (str) {
      return str.replace(camelizeRE, function (_, c) { return c ? c.toUpperCase() : ''; })
    });
    console.log(camelize('as-as'));
    //as---As
    

    自定义实现bind函数

    function bind(fn, ctx) {
        function boundFn(a) {
            var l = arguments.length;
            return l
                ? l > 1
                    ? fn.apply(ctx, arguments)
                    : fn.call(ctx, a)
                : fn.call(ctx)
        }
        // record original fn length
        boundFn._length = fn.length;
        return boundFn
    }
    

    将字符串转成数组的 toArray 方法

    function toArray(list, start) {
        start = start || 0;
        var i = list.length - start;
        var ret = new Array(i);
        while (i--) {
            ret[i] = list[i + start];
        }
        return ret
    }
    toArray('qwwqwq')
    //["q", "w", "w", "q", "w", "q"]
    

    extend 浅拷贝

    function extend(to, _from) {
        for (var key in _from) {
            to[key] = _from[key];
        }
        return to
    }
    extend({ aaa: 1 }, { bbb: 1 })
    //{aaa: 1, bbb: 1}
    

    关于浏览器判断

    var inBrowser = typeof window !== 'undefined';
    var UA = inBrowser && window.navigator.userAgent.toLowerCase();
    var isIE = UA && /msie|trident/.test(UA);
    var isIE9 = UA && UA.indexOf('msie 9.0') > 0;
    var isEdge = UA && UA.indexOf('edge/') > 0;
    var isAndroid = UA && UA.indexOf('android') > 0;
    var isIOS = UA && /iphone|ipad|ipod|ios/.test(UA);
    var isChrome = UA && /chrome\/\d+/.test(UA) && !isEdge;
    

    Set结构设置

    var _Set;
    /* istanbul ignore if */ // $flow-disable-line
    if (typeof Set !== 'undefined' && isNative(Set)) {
        // use native Set when available.
        _Set = Set;
    } else {
        // a non-standard Set polyfill that only works with primitive keys.
        _Set = /*@__PURE__*/ (function() {
            function Set() {
                this.set = Object.create(null);
            }
            Set.prototype.has = function has(key) {
                return this.set[key] === true
            };
            Set.prototype.add = function add(key) {
                this.set[key] = true;
            };
            Set.prototype.clear = function clear() {
                this.set = Object.create(null);
            };
    
            return Set;
        }());
    }
    

    数组的remove方法,不用再去find然后remove

    function remove (arr, item) {
        if (arr.length) {
        var index = arr.indexOf(item);
        if (index > -1) {
            return arr.splice(index, 1)
        }
        }
    }
    

    相关文章

      网友评论

        本文标题:关于vue源码工具函数系列总结(持续更新)

        本文链接:https://www.haomeiwen.com/subject/ougrdktx.html