算法导论学习总结-基础篇(一)

一、基础知识(概念)总结:
1.渐进记号:
(1).大O记号: 大O记号给出函数的渐进上界。定义:O(g(n))={f(n):存在正常量 c 和 n0,使得对所有 n>=n0,有 0<=f(n)<=cg(n)} ps:Θ记号是一个比O记号更强的概念。按集合论的写法,有 Θ(g(n)) 包含于 O(g(n))。
(2).大Ω记号:正如O记号提供了一个函数的渐进上界,Ω记号提供了渐进下界。定义:Ω(g(n)) = {f(n):存在正常量c和n0,使得所有n>=n0,有0<=cg(n)<=f(n)}
(3).大Θ记号:
大Θ记号给出函数的渐进紧确界。定义Θ(g(n)) = {f(n):存在正常数c1和c2和n0,使对所有的 n >= n0,都有 0 <= c1g(n) <= f(n) <= c2g(n)。0符号描述的两个边界,而大O和大Ω定义的只是上界和下界。
(4).小O记号:
用小O记号来表示一个非渐进紧确的上界。定义:O(g(n)) = {f(n):对任意正常量 C > 0,存在常量 n0 > 0,使得对所有 n >= n0,有 0 <= f(n) < cg(n)} ps:非渐进紧确的定义就是边界不包含等于号。
(5).小记号:
记号与Ω记号关系类似于小O标记和大O标记的关系。使用小表示非渐进紧确的下界。

2.NP完全问题:
NP完全或NP完备(NP-Complete,缩写为 NP-C 或 NPC),是计算复杂度理论中,决定性问题的等级之一。NPC 问题,是NP(非决定性多项式时间)中最难的决定性问题。因此NP完备问题应该是最不可能被化简为P(多项式时间可决定)的决定性问题的集合。许多人推测若任何NPC问题得到多项式时间的解法,那此解法就可应用在所有NP问题上。
(1)虽然迄今为止不曾找到对一个NP完全问题的有效算法,但是也没有人能证明NP完全问题确实不存在有效算法。换句话说,对于NP完全问题,是否存在有效算法是未知的。
(2)NP完全问题集具有一个非凡的性质:如果任何一个NP完全问题存在有效算法,那么NP完全问题都存在有效算法。
(3)有几个NP完全问题类似于(但有不完全同于)一些有着已知有效算法的问题。

3.几个排序算法效率回顾:
(1)稳定排序:
插入排序:

插入排序算法伪代码:
for j = 2 to A.length-1
    key = A[j]
    i = j - 1
    while i > 0 and A[i] > key
        A[i+1] = A[i]
        i = i - 1
    A[i + 1] = key  

简述:最好情况下,序列已经是有序排列的了,这种情况下,需要进行比较操作需(n-1)次即可。最坏情况下,序列是降序排列的,那么此时需要进行比较共有 n(n-1)/2次。所以最差时间复杂度为 O(nn),最优时间复杂度为 O(n),平均时间复杂度为 O(nn)。最差空间复杂度为 O(n),需要辅助空间度为 O(1)

冒泡排序:

冒泡排序算法伪代码:
for i=1 to A.length-1
    for j = i-1 to A.length-2
        if(A[j] > A[j+1])
            swap(A[j],A[j+1])

简述:冒泡排序在最好情况下(序列已经有序)和最坏情况下的时间负责度都是O(n*n),所以看插入排序在序列相对有序的情况下,性能会优于冒泡排序。

桶排序:

桶排序算法伪代码:
for i = 0 to A.length-1
    //将链表中的元素按照function指定的规则放入桶中
    put A[i] to bucket[function(A[i])]
for j = 0 to buctkets.length-1
    //插入排序对每个桶进行排序
    insertSort(bucket[j])
//将各个桶中的元素join在一起
join(bucket[j])

简述:桶排序的平均时间复杂度为线性的O(N+C),其中C=N(logN - logM) N是待排序的数列的长度,M是桶的个数。ps:桶的数量M越大,其效率就越高,最好的时间复杂度达到O(N)。桶排序的空间复杂度为O(N+M)。

计数排序(Counting sort):

COUNTING-SORT(A,B,k)
    let C[0..k] be a new array
    //初始化数组
    for i = 0 to k
        C[i] = 0
    //将A[j]出现的次数记录在C[A[j]]的位置
    for j = 1 to A.length
        C[A[j]] = C[A[j]] + 1
    //将相邻两项相加,保存在当前项,这个主要用来处理重复值
    for i = 1 to k
        C[i] = C[i] + C[i-1]
    //遍历原来的数据,将其排序
    for j = A.length downto 1
        B[C[A[j]] = A[j]
        C[A[j]] = C[A[j]]-1

简述:这个伪代码看起来比较难理解,(详细解释可以参考算法导论第三版P109)。计数排序不是一个比较的排序算法,其最差、最优、平均时间复杂度均为 O(n+k),最差空间复杂度为O(n+k)。计数排序效率优于任何比较排序算法,因为其不是比较排序算法,所以也就突破了排序算法Ω(nlgn)的限制。
ps:算法通俗的理解就是:例如有10个年龄不同的人,统计出有8个人的年龄比A小,那么A的年龄就排在第9位。

4.最大子数组:在一个数据中,相邻的几个元素的和最大的子数据组称为元数组的最大子数组。

5.矩阵乘法的定义:若A=a(ij)和B=b(ij)是nn的方阵,则对i,j=1,2,...,n,定义乘积 C=AB中元素c(ij)为:

矩阵乘法运算伪代码:
n = A.rows
let C be a new n*n matrix
for i = 1 to n
    for j = 1 to n
        c(ij) = 0
        for k = 1 to n
            c(ij) = c(ij)+a(ik)*b(kj)
return C

你可能感兴趣的:(算法导论)