记录几个前端笔/面试中常遇到的算法

记录几个前端笔面试中遇到的算法

1、冒泡排序

function bubble_sort(A) {
    var l = A.length
    for (var i = 0; i < l; i ++) {
        for (var j = 0; j < l - i - 1; j ++) {
            if(A[j] > A[j + 1]) {
                var temp = A[j]
                A[j] = A[j + 1]
                A[j + 1] = temp
            }
        }
    }
}

冒泡排序就比较简单了,时间复杂度O(n^2)

2、快速排序

function quick_sort(A, p = 0, r = A.length - 1) {
    if (p < r){
        var q = partation(A, p, r)
        quick_sort(A, p, q - 1)
        quick_sort(A, q + 1, r)
    }
}
function partation(A, p, r) {
    var x = A[r]
    var i = p - 1
    for (var j = p; j < r; j ++) {
        if (A[j] <= x) {
            i += 1
            var temp = A[i]
            A[i] = A[j]
            A[j] = temp
        }
    }
    A[r] = A[i + 1]
    A[i + 1] = x
    return i + 1
}

快速排序是很多面试官喜欢问的,也是比较常用的,时间复杂度O(nlg(n))

3、插入排序

function insert_sort(A) {
    for (var j = 1; j < A.length; j ++) { var key = A[j] var i = j - 1 while (i >= 0 && A[i] > key) { A[i + 1] = A[i] i -= 1 }
        A[i + 1] = key
    }
}

插入排序也比较简单,时间复杂度O(n^2)

4、堆排序(维护最大堆)

function max_heap(A, i) {
    var l = i * 2 + 1
    var r = (i + 1) * 2
    var largest = i
    var size = A.heapSize
    if(l < size && A[l] > A[i]) { largest = l }
    if (r < size && A[r] > A[largest]) { largest = r }
    if (largest !== i) { var temp = A[i] A[i] = A[largest] A[largest] = temp max_heap(A, largest) }
}
function build_heap(A) {
    var l = A.heapSize
    for (var i = l / 2 - 1; i >= 0; i --) { max_heap(A, i) }
}
function heap_sort(A) {
    var l = A.length
    A.__proto__.heapSize = A.length
    build_heap(A)
    for (var i = l - 1; i > 0; i --) { var temp = A[i] A[i] = A[0] A[0] = temp A.__proto__.heapSize -= 1 max_heap(A, 0) }
}

堆排序是比较好的排序算法,时间复杂度最坏O(nlgn)

5、寻找第i小的值

function find_partation(A, p, r) {
var key = A[r]
    var i = p - 1
    for (var j = p; j <= r - 1; j ++) {
        if (A[j] < key) {
            i += 1
            var temp = A[i]
            A[i] = A[j]
            A[j] = temp
        }
    }
    A[r] = A[i + 1]
    A[i + 1] = key
    return i + 1
}

function twoPart_find(A, p, r, i) {
    if (p === r) {
        return A[p]
    }
    var q = find_partation(A, p, r)
    var k = q - p + 1
    if (i === k) {
        return A[q]
    } else if (i < k) {
        return twoPart_find(A, p, q - 1, i)
    } else {
        return twoPart_find(A, q + 1, r, i - k)
    }
}

这个算法其实有一部分跟快排是一样的,先进行划分,然后在一半里面递归寻找,时间复杂度O(nlgn)

6、二分查找

function twoPart_find(A, p, r, i) {
if (p === r) {
        return A[p]
    }
    var q = find_partation(A, p, r)
    var k = q - p + 1
    if (i === k) {
        return A[q]
    } else if (i < k) {
        return twoPart_find(A, p, q - 1, i)
    } else {
        return twoPart_find(A, q + 1, r, i - k)
    }
}

二分查找比较简单,因为是有序的数组,递归调用即可,时间复杂度O(lgn)

7、取两个数组的交集

function findSame(A, B) {
var Al = A.length
    var Bl = B.length
    var temp = [], result = []
    for(var i = 0; i < Al; i ++) { if (!temp[A[i]]) { temp[A[i]] = 1; }
    }
    for (var j = 0; j < Bl; j ++) { if (temp[B[j]]) { temp[B[j]] = 0 result.push(B[j]) }
    }
    return result
}

这个也比较简单,使用hash实现的,方法简单得益于js中可以直接给数组的某一下标赋值,在平时很多小伙伴不喜欢用hash计算,其实hash还是很好用的。方法实现了去重求交集。时间复杂度O(m+n)

先发这几个,之后进行补充…

点赞