破解加密狗軟件

// promise.all 實現
// promise.all(iterable)返回一個新的promise實例。
// 此實例在iterable參數內全部的promise都fulfilled或者參數中不包含promise時,狀態才變成fulfilled;
// 若是參數中有一個失敗rejected,此實例回調失敗,失敗的信息是第一個失敗promise的返回結果

Promise.all_ = function(promises) {
    return new Promise((resolve, reject) => {
        // Array.from()可將可迭代對象轉化爲數組
        promises = Array.from(promises);
        if(promises.length===0) {
            resolve([]);
        } else {
            let result = [];
            let index = 0;
            for(let i=0; i<promises.length; i++) {
                // 考慮到promise[i]多是thenable對象也多是普通值
                Promise.resolve(promises[i]).then(data => {
                    result[i] = data;
                    if(++index===promises.length) {
                        // 全部的promise狀態都是fulfilled,promise.all返回的實例才變成fulfilled狀態
                        resolve(result);
                    }
                }, err => {
                    reject(err);
                    return;
                })
            }
        }
    })
}

複製代碼

3.Promise.race實現

// promise.race
// Promise.race返回的仍然是一個Promise,它的狀態與第一個完成的Promise的狀態相同;
// 若是傳入的參數是不可迭代的,那麼將會拋出錯誤。

Promise.ra_ce = function(promises) {
    promises = Array.from(promises);
    return new Promise((resolve, reject) => {
        if(promises.length===0) {
            return;
        } else {
            for(let i=0; i<promises.length; i++) {
                Promise.resolve(promises[i]).then(data => {
                    resolve(data);
                    return;
                }, err => {
                    reject(err);
                    return;
                })
            }
        }
    })
}
複製代碼

4. call實現

// 模擬思路:
// 將函數設爲對象的屬性
// 執行該函數
// 刪除該函數
Function.prototype.call2 = function (context) {
    // 將函數設爲對象的屬性,改變this指向(傳null的時候,this指向window)
    context = context || window;
    context.fn = this;
    // 傳參並執行函數,用一個數組來接收不定長參數
    var args = [];
    for(var i = 1; i < arguments.length; i ++){
        args.push('arguments['+i+']');
    }
    var result = eval('context.fn(' + args + ')');
    //刪除該函數
    delete context.fn;
    return result;
}
複製代碼

5. apply實現

// 模擬apply()方法的實現

Function.prototype.apply2 = function(context,arr){
    context = context || window;
    context.fn = this;
    var result;
    if(!arr){
        result = context.fn()
    }else{
        var args = [];
        for(var i = 0; i < arr.length; i++){
            args.push('arr[' + i + ']')
        }
        result = eval('context.fn(' + args + ')')
    }
    delete context.fn;
    return result;
}
複製代碼

6. bind實現

// 模擬bind的實現
// bind() 方法會建立一個新函數。當這個新函數被調用時,bind() 的第一個參數將做爲它運行時的 this,以後的一序列參數將會在傳遞的實參前傳入做爲它的參數。
// 1.返回一個函數
// 2.能夠傳入參數
//   傳參時注意:函數能夠只傳一個參數,而後在執行返回的函數時再繼續傳參
// 3.bind函數能夠用new來建立對象,至關於把原函數看成一個構造器,即當bind返回的函數做爲構造函數的時候,bind指定的this失效了
// 4.調用bind的不是函數時要報錯

Function.prototype.bind2 = function(context){
    if(typeof this !== "function"){
        throw new Error("")
    }
    var self = this;
    var args = Array.prototype.slice.call(arguments,1);
    var fNOP = function(){}
    var fBound =  function(){
        var bindArgs = Array.prototype.slice.call(arguments);
        self.apply(self instanceof fNOP ? this : context,args.concat(bindArgs));
    }
    fNOP.prototype = this.prototype;
    fBound.prototype = new fNOP();
    return fBound;
}

複製代碼

7. 繼承方法

// 構造函數繼承
function Person1(name) {
    this.name = name;
}

function Student1(name, age) {
    Person1.call(this, name);
    this.age = age;
}
var s1 = new Student1("xuhanlin");
console.log(s1.name);


// 原型鏈繼承
function Person2() {
    this.name = "renyuan";
}

function Student2(age) {
    this.age = age;
}
Student2.prototype = new Person2();
var s2 = new Student2();
console.log(s2.name);

// 組合繼承
function Person3() {
    this.name = "renyuan";
}

function Student3() {
    Person3.call(this);
    this.age = "18";
}
Student3.prototype = new Person3();
var s3 = new Student3();
console.log(s3.name, s3.age);

複製代碼

8.閉包

// 閉包實現倒計時
for(var i = 10; i > 0; i--){
    (function(i){
        setTimeout(() => {
        console.log(i);
    },(10-i)*1000)
    })(i)
}
複製代碼

9.防抖

function debounce(func,wait){
    var timeout;
    return function(){
        var context = this;
        var args = arguments;
        clearTimeout(timeout);
        timeout = setTimeout(function(){
            func.apply(context,args);
        },wait);
    }
}
複製代碼

10.節流

// 使用時間戳
// 當觸發事件的時候,咱們取出當前的時間戳,而後減去以前的時間戳(最一開始值設爲 0 )
// 若是大於設置的時間週期,就執行函數,而後更新時間戳爲當前的時間戳,
// 若是小於,就不執行。
function throttle(func,wait){
    return function(){
        var context = this;
        var args = arguments;
        var previous = 0;
        var now = +new Date();
        if(now - previous > wait){
            func.apply(context,args);
            previous = now;
        }
    }
}

// 設置定時器
function throttle(func,wait){
    var timeout;
    return function(){
        var context = this;
        var args = arguments;
        if(!timeout){
          timeout = setTimeout(function(){
              timeout = null;
            func.apply(context,args)
        },wait);  
        }
        
    }
}
複製代碼

11.new實現

function create(Con, ...args) {
  let obj = {}
  Object.setPrototypeOf(obj, Con.prototype)
 //或者 obj.__proto__ = Con.prototype
  let result = Con.apply(obj, args)
  return result instanceof Object ? result : obj
}
複製代碼

12.數組去重

var array = [1,1,'1'];

// 方法一:indexOf()
// 建立一個新數組,遍歷原數組,用indexOf判斷原數組中的值是否已經存在,不存在就push進去
function unique(arr){
    var res = [];
    for(let item of arr){
        if(res.indexOf(item) === -1){
            res.push(item);
        }
    }
    return res;
}


// 方法二:排序後去重
function unique(arr){
    var res = [];
    var newArr = arr.sort();
    for(let i=0; i<newArr.length; i++){
        if(newArr[i] !== newArr[i+1]){
            res.push(newArr[i]);
        }
    }
    return res;
}

// 方法三:利用Set的惟一性
function unique(arr){
    return Array.from(new Set(arr));
}

// 方法四:Map
function unique (arr) {
    const map = new Map()
    return arr.filter((a) => !map.has(a) && map.set(a, 1))
}

console.log(unique(array));

複製代碼

13.數組扁平化

var arr = [1, [2, [3, 4]]];

// 方法一:循環數組,若是裏面仍是數組,遞歸調用扁平化方法
function flatten(arr) {
    var result = [];
    for (let i = 0; i < arr.length; i++) {
        if (Array.isArray(arr[i])) {
            result = result.concat(flatten(arr[i]));
        } else {
            result.push(arr[i])
        }
    }
    return result;
}

// 方法一的改進寫法
function flatten(arr) {
    return arr.reduce(function (pre, item) {
        return pre.concat(Array.isArray(item) ? flatten(item) : item)
    }, []);
}

// 方法二:toString(),它的一個缺點是改變了元素的類型,只適合於數組中元素都是整數的狀況
function flatten(arr) {
    return arr.toString().split(",").map(function (item) {
        return +item;
    })
}

console.log(flatten(arr));
複製代碼

14.柯里化

15.快速排序

// 快速排序
// 找到一個基準數,比基準數小的放左邊,比基準數大的放右邊
// 對左右區間不斷重複這個過程

var quickSort = function(arr){
    if(arr.length <= 1){
        return arr;
    }
    const pivotIndex = Math.floor(arr.length / 2); //任意基準數索引
    const pivot = arr.splice(pivotIndex,1)[0]; //找到對應的基準數
    const left = [];
    const right = [];
    for(let i=0; i<arr.length; i++){
        if(arr[i] < pivot){
            left.push(arr[i]);
        }else{
            right.push(arr[i]);
        }
    }
    return quickSort(left).concat([pivot], quickSort(right));
}

const arr = [98, 42, 25, 54, 15, 3, 25, 72, 41, 10, 121];
console.log(quickSort(arr));
複製代碼

16.冒泡排序

// 冒泡排序
// 兩兩相鄰元素對比,若是前一個比後一個大,就日後移,一輪比較下來,最大的數到了最後一個
// 重複這個步驟

function bubbleSort(arr) {
    for (let i = 0; i < arr.length; i++) {
        for (let j = 0; j < arr.length - 1 - i; j++) {
            if (arr[j] > arr[j + 1]) {
                const temp = arr[j];
                arr[j] = arr[j + 1];
                arr[j + 1] = temp;
            }
        }
    }
    return arr;
}

var arr = [10, 14, 8, 5, 88];
console.log(bubbleSort(arr));
複製代碼

17.深淺拷貝

// 實現淺拷貝
// 遍歷對象,而後把屬性和屬性值都放到一個新對象裏
var shallowCopy = function(obj) {
    // 只拷貝對象
    if (typeof obj !== 'object') return;
    // 根據obj的類型判斷是新建一個數組仍是對象
    var newObj = obj instanceof Array ? [] : {};
    // 遍歷obj,而且判斷是obj的屬性才拷貝
    for (var key in obj) {
        if (obj.hasOwnProperty(key)) {
            newObj[key] = obj[key];
        }
    }
    return newObj;
}


// 實現深拷貝
// 在拷貝的時候判斷一下屬性值的類型,若是是對象,再遞歸拷貝一下
var deepCopy = function(obj){
    if(typeof(obj) !== "object") return;
    var newObj = obj instanceof Array ? [] : {};
    for(let key in obj){
        if(obj.hasOwnProperty(key)){
            newObj[key] = typeof obj[key] === "object" ? deepCopy(obj[key]) : obj[key];
        }
    }
    return newObj;
}
相關文章
相關標籤/搜索