函數技巧總結

記錄一些實用的函數技巧

 

  包含大量實用函數,持續更新中。vue

一、尤大的強綁bind實現(聽說比原生還快一點)node

    //傳入強綁函數與上下文
    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)
        }
        //保存傳入函數形參數
        boundFn._length = fn.length;
        return boundFn
    }
    //示例
    var obj = {
        a: 1
    }
    var fn = bind(function(n1, n2) {
        console.log(this.a);
        console.log(n1 + n2);
    }, obj);
    fn(1, 2); //1 3

  使用方法也很簡答,傳入函數與強綁上下文,再傳入參數執行。ajax

 

二、事件觸發節流閥數組

  該方法來源於偉大的jQuery做者,john ***!瀏覽器

    // 節流函數與最低觸發事件
    function delayFn(fn, delay) {
        var timer = false;
        // 滾動觸發
        window.onscroll = function() {
            timer = true;
        };
        // 每隔一段時間觸發指定函數
        setInterval(function() {
            if (timer) {
                timer = false;
                fn();
            }
        }, delay);
    }

  這個函數也至關簡單,用於滾動事件的監聽。因爲滾動會很是頻繁的觸發onscroll,因此設定一個觸發頻率能夠極大的優化瀏覽器性能。緩存

 

三、緩步加載函數app

  該函數應用場景主要是後臺提供了大量的數據須要渲染到頁面,然而直接拼接字符串+innerHTML會致使假卡死,用戶體驗極差。dom

  雖說這個問題的源頭就是錯誤的,可是也有一些補救的辦法。函數

    // 假設經過ajax請求到一個包含大量數據的數組
    ajax('url', function(result) {
        var data = result;
        fps(data, 1000, 1000, function(data) {
            console.log(data);
        });
    });
    // cut爲每次處理的數量
    // delay爲每次處理的間隔時間
    function fps(data, cut, delay, fn) {
        // 對剩餘數量作檢測
        var res = data.length < cut ? data.splice(0, data.length) : data.splice(0, cut);
        fn(res);
        if (data.length > 0) {
            // 下一批數據的處理會在下一個task中進行
            setTimeout(fps, delay);
        }
    }

  本身手寫的,比較簡單,大概思想出來就行了嘛~性能

 

四、插入一個深拷貝函數

    // 接受變量與類型
    function type(el, type) {
        return Object.prototype.toString.call(el).slice(8, -1) === type;
    }
    // 深拷貝 目標對象與拷貝對象
    function deepCopy(tar, obj) {
        var tar = tar || {},
            el, clone;
        for (var key in obj) {
            el = obj[key];
            if (type(el, 'Object') || type(el, 'Array')) {
                clone = type(el, 'Object') ? {} : [];
                tar[key] = deepCopy(clone, el);
            } else {
                tar[key] = el;
            }
        }
        return tar;
    }
    // 使用方法
    var obj = {
        a: [1],
        b: {
            a: 1
        }
    };
    var obj2 = {};
    deepCopy(obj2, obj);

 

五、數組去重

  來自於jQuery源碼:

    // 去重
    function duplicate(arr) {
        var len = arr.length,
            num = 0,
            res = [];
        // 先進行排序
        arr.sort((a, b) => a - b);
        // 找出全部相鄰重複元素索引
        for (var i = 0; i < len; i++) {
            if (arr[i] === arr[i + 1]) {
                res.push(i);
                num++;
            }
        }
        //依次刪除
        while (num--) {
            arr.splice(res[num], 1);
        }
        return arr;
    }

 

 六、數組亂序

  打亂數組,俗稱洗牌,方法超級簡單易懂,可是可能很low。不要緊!能夠多循環幾回!

    // 返回隨機數
    function getR(len) {
        return Math.floor(Math.random() * len);
    }
    // 打亂數組
    function randomArr(arr) {
        var len = arr.length,
            j;
        for (var i = 0; i < len; i++) {
            // 獲取隨機索引
            j = getR(len);
            // 交換位置
            [arr[i], arr[j]] = [arr[j], arr[i]];
        }
        return arr;
    }

 

 七、緩存函數

  來源於vue源碼:

    // 有時候可能須要默認緩存對象
    function cached(fn, cache) {
        var cache = cache || Object.create(null);
        // 返回一個函數
        return (function cachedFn(str) {
            var hit = cache[str];
            return hit || (cache[str] = fn(str))
        })
    }

  默認狀況下建立一個純淨對象用來作緩存,固然也能夠選擇本身傳入一個帶有默認值得緩存對象。

 

八、惰性求值函數

  適用於兼容性判斷,第一次加載重寫函數,第二次跳過判斷邏輯。

    var a = 1;
    // 惰性加載函數
    function lazy(el) {
        // 第一次作判斷
        if (el === 1) {
            // 而後重寫函數
            lazy = function() {
                return 1;
            }
        } else if (el === 2) {
            lazy = function() {
                return 2;
            }
        }
        return lazy();
    }
    console.log(lazy(a)); //1
    // 第二次調用跳過判斷環節
    console.log(lazy(a)); //1
    console.log(lazy(a)); //1
    console.log(lazy(a)); //1
    console.log(lazy(a)); //1

  

 九、遍歷DOM樹

  超級簡單!!!一看就會

    // 遍歷DOM樹
    function walkDom(node, fn) {
        fn(node);
        // 使用該方法避免回車會致使空行 
        node = node.firstElementChild;
        while (node) {
            walkDom(node, fn);
            node = node.nextElementSibling;
        }
    }
    // 示例
    var div = document.getElementsByTagName('div')[0];
    walkDom(div, function(el) {
        console.log(el.tagName);
    });

 

十、快速生成16進制顏色

  超級簡單!!!

    function getHexColor() {
        return '#' + Math.random().toString(16).substr(2, 6);
    }

 

  先寫這幾個了!

相關文章
相關標籤/搜索