算法导论

MIT Introduction to Algorithms 学习笔记(十)

随声附和 提交于 2020-03-01 20:52:18
Lecture 9: Hashing II: Table Doubling,Karp-Rabin 散列表应该有多大 ? 理想状态 : 根据需要改变大小 . ( 重散列 )Rehashing 增长 : 散列表长度成倍增长是个好选择 . 删除 : 字符串匹配 (String Matching) Simple Algorithm: Karp-Rabin Algorithm: python代码: def karp_rabin(T, P): n = len(T) m = len(P) d = 256 q = 101 h = d ** (m - 1) % q p = 0 t = 0 for i in range(m): p = (d*p + ord(P[i])) % q t = (d*t + ord(T[i])) % q for s in range(n - m + 1): print(s,p,t) if p == t and T[s:s+m] == P: return s if s < n - m: t = ( d * ( t - ord( T[s] ) * h ) + ord( T[s + m] ) ) % q 来源: oschina 链接: https://my.oschina.net/u/106593/blog/604576

《算法导论(第三版)》笔记——堆排序(Heapsort)

强颜欢笑 提交于 2020-02-29 11:22:41
堆排序是利用数据结构 堆 (heap),进行排序的一种方式。理解起来需要花费一番功夫。笔者在阅读《算法导论》之后,根据伪代码写出了代码,现附录于下,建议配合原书中图片一起理解。 测试代码 先给出测试代码,因为其中定义的一些全局变量可能下面的函数需要使用。先注意里面的全局变量,至于调用的函数是什么意思,下面会有解释。 # include <iostream> using namespace std ; //0占去A[0]; int A [ ] = { 0 , 16 , 14 , 10 , 9 , 8 , 7 , 4 , 3 , 2 , 1 } ; //从A[1]开始。算作第一个。所以A的长度减一(减去A[0]) int length = sizeof ( A ) / sizeof ( int ) - 1 ; //length之后要改变,所以和k分开。 int k = sizeof ( A ) / sizeof ( int ) - 1 ; //镶嵌函数部分。 int main ( ) { for ( int i = 1 ; i <= k ; i ++ ) { Left ( i ) ; Right ( i ) ; Parent ( i ) ; } Heapsort ( A ) ; for ( int i = 1 ; i <= k ; i ++ ) { cout << A [ i ] <<

算法导论:Trie字典树

a 夏天 提交于 2020-02-23 15:13:45
1、 概述 Trie树,又称字典树,单词查找树或者前缀树,是一种用于快速检索的多叉树结构,如英文字母的字典树是一个26叉树,数字的字典树是一个10叉树。 Trie一词来自re trie ve,发音为/tri:/ “tree”,也有人读为/traɪ/ “try”。 Trie树可以利用字符串的公共前缀来节约存储空间。如下图所示,该trie树用10个节点保存了6个字符串pool、prize、preview、prepare、produce、progress 在该trie树中,字符串preview,prepare公共前缀是“pre”,因此可以只存储一份“pre”以节省空间。当然,如果系统中存在大量字符串且这些字符串基本没有公共前缀,则相应的trie树将非常消耗内存,这也是trie树的一个缺点。 Trie树的基本性质可以归纳为: (1)根结点不包含字符,除根节点意外每个结点只包含一个字符。 (2)从根结点到某一个结点,路径上经过的字符连接起来,为该结点对应的字符串。 (3)每个结点的所有子结点包含的字符串不相同。 注意:每个结点可以有没有或者一个或者多个字结点,叶子结点没有子结点 2、数据结构表示 /** * 定义字典树的数据结构 * c 当前节点值 * isLeaf 是否是叶子结点 * children 孩子,key是孩子结点值,value是孩子结点的下一个字典树 * */ class

【算法导论】贪心算法,递归算法,动态规划算法总结

主宰稳场 提交于 2020-02-23 10:26:55
一般实际生活中我们遇到的算法分为四类: 一>判定性问题 二>最优化问题 三>构造性问题 四>计算性问题 而今天所要总结的算法就是着重解决 最优化问题 《算法之道》对三种算法进行了归纳总结,如下表所示: 标准分治 动态规划 贪心算法 适用类型 通用问题 优化问题 优化问题 子问题结构 每个子问题不同 很多子问题重复(不独立) 只有一个子问题 最优子结构 不需要 必须满足 必须满足 子问题数 全部子问题都要解决 全部子问题都要解决 只要解决一个子问题 子问题在最优解里 全部 部分 部分 选择与求解次序 先选择后解决子问题 先解决子问题后选择 先选择后解决子问题 分治算法特征: 1)规模如果很小,则很容易解决。//一般问题都能满足 2)大问题可以分为若干规模小的相同问题。//前提 3)利用子问题的解,可以合并成该问题的解。//关键 4)分解出的各个子问题相互独立,子问题不再包含公共子问题。 //效率高低 【一】动态规划: 依赖:依赖于有待做出的最优选择 实质:就是分治思想和解决冗余。 自底向上(每一步,根据策略得到一个更小规模的问题。最后解决最小规模的问题。得到整个问题最优解) 特征:动态规划任何一个i+1阶段都仅仅依赖 i 阶段做出的选择。而与i之前的选择无关。但是动态规划不仅求出了当前状态最优值,而且同时求出了到中间状态的最优值。 缺点:空间需求大。 【二】贪心算法: 依赖

【算法导论】贪心算法,递归算法,动态规划算法总结

痴心易碎 提交于 2020-02-23 10:24:55
一般实际生活中我们遇到的算法分为四类: 一>判定性问题 二>最优化问题 三>构造性问题 四>计算性问题 而今天所要总结的算法就是着重解决 最优化问题 《算法之道》对三种算法进行了归纳总结,如下表所示: 标准分治 动态规划 贪心算法 适用类型 通用问题 优化问题 优化问题 子问题结构 每个子问题不同 很多子问题重复(不独立) 只有一个子问题 最优子结构 不需要 必须满足 必须满足 子问题数 全部子问题都要解决 全部子问题都要解决 只要解决一个子问题 子问题在最优解里 全部 部分 部分 选择与求解次序 先选择后解决子问题 先解决子问题后选择 先选择后解决子问题 分治算法特征: 1)规模如果很小,则很容易解决。//一般问题都能满足 2)大问题可以分为若干规模小的相同问题。//前提 3)利用子问题的解,可以合并成该问题的解。//关键 4)分解出的各个子问题相互独立,子问题不再包含公共子问题。 //效率高低 【一】动态规划: 依赖:依赖于有待做出的最优选择 实质:就是分治思想和解决冗余。 自底向上(每一步,根据策略得到一个更小规模的问题。最后解决最小规模的问题。得到整个问题最优解) 特征:动态规划任何一个i+1阶段都仅仅依赖 i 阶段做出的选择。而与i之前的选择无关。但是动态规划不仅求出了当前状态最优值,而且同时求出了到中间状态的最优值。 缺点:空间需求大。 【二】贪心算法: 依赖

数据结构与算法推荐书单

試著忘記壹切 提交于 2020-02-22 00:21:03
  对于入门的同学不建议过度追求看上去很经典的书籍,例如:《算法导论》/《算法》这些书。可以看一些相对容易看的书来入门,例如《大话数据结构》、《算法图解》。   《大话数据结构》这本书最大的特点是它将理论讲的非常有趣,不枯燥。而且每个数据结构和算法作者都结合生活中的例子进行讲解,虽然这本书有400+页,但是花两天事件读完应该是没有问题的。如果之前完全不懂数据结构和算法,可以从这本书开始。   《算法图解》和《大话数据结构》走得是同样的路线。“像小说一样有趣的算法入门书籍”,通俗易懂。它只有不到200页,所以内容比较少。看看这本书,能够让你对数据结构和算法有 个大概的认识。   入门书籍共同的问题是缺少细节,不够系统,有不够严谨。如果想系统的学习学习数据结构和算法仅靠这两本书是不够的。   《数据结构和算法分析》国内外有很多大学拿这本书当作教材。这本书非常系统/全面/严谨,而且不是特别难,适合对数据结构有一定的了解,同时至少掌握了一门编程语言的人。这本书有三个版本:《数据结构与算法分析:C语言描述》/ 《数据结构与算法分析:C++描述》/ 《数据结构与算法分析:java语言描述》。   如果你熟悉的是其它编程语言可以看一下《数据结构与算法JavaScript描述》/ 《数据结构与算法:Python语言描述》。 面试刷题宝典:   《剑指offer》这本书的作者写作目的本明确

【算法导论】学习笔记——第9章 中位数和顺序统计量

99封情书 提交于 2020-02-19 22:43:03
在一个由n个元素组成的集合中,第i个 顺序统计量 (order statistic)是该集合中第i小的元素。用非形式化的描述来说,一个 中位数 (median)使它所属集合的“中点元素”。当n为奇数时,中位数是唯一的,位于i=(n+1)/2处。当n为偶数时,存在两个中位数,分别位于i=n/2和i=n/2+1处。因此不考虑n的奇偶性,中位数总是出现在i=floor((n+1)/2)处(下中位数)与i=ceil((n+1)/2)处(上中位数)。 本章将讨论一个由n个互异的元素构成的集合中选择第i个顺序统计量的问题。将这一问题形式化定义为如下的选择问题: 输入 :一个包含n个(互异)数的集合A和一个整数:1<=i<=n。 输出 :元素x属于A,且A中恰有i-1个其他元素小于它。 1. 最大值和最小值 在一个有n个元素的集合中,通过n-1次比较可找到其中的最小值。代码如下: 1 int Minimum(int A[], int n) { 2 int min = A[1]; 3 int i; 4 5 for (i=2; i<=n; ++i) 6 if (min > A[i]) 7 min = A[i]; 8 return min; 9 } 采用同样的方式,可通过2n-2次比较同时找到最大值和最小值。而事实上,仅需3*floor(n/2)次比较就可以找到最小值和最大值。即先成对比较后

算法导论 Exercises 9.3-6

时间秒杀一切 提交于 2020-02-19 22:30:31
Problem Description: The kth quantiles of an n-element set are the k - 1 order statistics that divide the sorted set into k equal-sized sets (to within 1). Give an O(n lg k)-time algorithm to list the kth quantiles of a set. 问题描述: 一个集合的第k分位数是指这样k - 1个数: 若将一个大小为n的集合从小到大排好序,这k - 1个数能将这个有序的数列分为k组,并且每组元素的个数相差不超过1。 现给出一个长为n的数组(无序),要求以 O(n lg k) 的时间复杂度找到其 k 分位数。 比如: 8 4 5 3 2 6 1 7 9 排序后是 1 2 3 4 5 6 7 8 9 其 3 分位数是 3 6,将排序后的数列分成 1 2 3; 4 5 6; 7 8 9 三段,每段元素个数均为3。 2 9 3 4 3 3 9 1 3 8 1 排序后是 1 1 2 3 3 3 3 4 8 9 9 其 4 分位数是 2 3 8,将排序后的数列分成 1 1 2; 3 3 3; 3 4 8; 9 9 四段,每段元素个数分别为 3 3 3 2。 解决方案: 首先

【转】acm学习方法

混江龙づ霸主 提交于 2020-02-16 11:35:11
建议 做到50行以内的程序不用调试、100行以内的二分钟内调试成功. acm主要是考算法的,主要时间是花在思考算法上,不是花在写程序与debug上。 算法集锦 https://www.cnblogs.com/ngyifeng/p/3718601.html 书籍推荐 入门三本: 《数据结构与算法》(傅清祥,王晓东编著,我所见过的最好的算法教材) 程序设计导引及在线实践 作者: 李文新 ACM程序设计培训教程 吴昊 基础提高: 算法设计与分析 这是国内牛人王晓东的大作,非常不错的算法书 算法设计与试验题解 王晓东 计算几何-算法设计与分析 周培德 组合数学 第三版 冯舜玺 译 算法艺术与信息学竞赛 刘汝佳的杰作,引导着信息学竞赛的发展 如果算法导论是九阳神功,那这本无疑就是九阴真经。本书是专为参加一些诸如ACM之类程序设计比赛的同学而写的,江湖人称“黑书”。里面讲的都是一些在编程比赛中常用的算法、数据结构,以及一些数论和计算几何等。我虽然并不搞竞赛,但也从此书中受益颇多。 国际信息学奥林匹克竞赛指导— — 实用算法的分析与程序设计  吴文虎 王建德 Introduction to Algorithm 科曼著 传说中的宝典 算法导论(原书第3版) Algorithms 算法概论 短小精悍,别据一格,准经典之作。一个坏消息: 同算法导论,该书没有习题答案。好消息:习题很经典,难度也适中

算法导论系列笔记之线性时间排序

家住魔仙堡 提交于 2020-02-14 17:55:39
线性时间排序 以下为本人整理课程笔记 课程地址: b站搬运 github: 还有除了算法导论外一些基础知识的笔记 我们能做到的排序有多快? 速度取决于计算模型【哪些操作是被允许的】 比较排序的算法模型 在模型中只能进行两两之间的大小比较来决定顺序 快速排序 归并排序 插入排序 堆排序 定理 比较排序的算法速度不会超过 nlgn 决策树 举例3个数进行比较排序的决策树 每一个内部节点都会有一个下标为i:j标记,左孩子为小于等于,右孩子为大于 每一个叶结点表示一个排序结果,其中有一个是正确的特定排序 决策树模型 构建可以接收n个数进行比较的一个决策树【至少一个 就是把算法中可能的结果都列出来 树的叶子结点与n的阶乘有关,树的大小与n的指数有关 运行时间与树的高度 以此去证明比较排序的下界为 nlgn 证明 n!<=2^h 【lgn为单调递增函数 h>=lg(n!) 确定性算法:它执行的每一步都是完全正确的 如果是随机算法,就会得到不止一个树,而是一个概率分布的多种 线性时间内完成 计数排序 假定要排序的是n个整数,每个整数都在1到k的范围内,需要辅助存储序列 伪代码 COUNTING-SORT(A,B,k) let C[0…k] be a new array //记录各个数出现的频率 for i=0 to k C[i] = 0 for j=1 to A.length C[A[j]] =