邓俊辉 数据结构与算法C++版 第十三章 串 ADT
邓公数据结构与算法 第十三章 串
- ADT
- 定义和特点
- 术语
- ADT接口实现
- 模式匹配
- 问题与需求
- 算法测试方法
- 蛮力匹配
- 构思
- 蛮力匹配:版本1
- 蛮力匹配:版本2
- 蛮力匹配:性能分析
- KMP算法
- next【】表
- 理解next【】表
- 构造next【】表
- next【】表代码实现
- KMP复杂度准确分析 ——线性时间O(n)
- KMP算法改进版
- BM_BC算法
- 动机——bc【】表
- 坏字符
- 构造bc【】
- 最好情况—— O(n/m)
- 最坏情况—— O(n*m)
- BM_GS算法
- 好后缀策略
- 概念
- 实例
- 构造GS表
- 性能
- Karp-Rabin 算法:串即是数
- 凡物皆数
- 串亦是数
- 数位溢出
- 散列压缩
- 散列冲突
- 快速指纹计算
ADT
定义和特点
特点:串长远远大于字符种类
术语
ADT接口实现
模式匹配
问题与需求
主要解决4个问题。
算法测试方法
成功与失败的情况分开来测试。
蛮力匹配
构思
- 自左向右,以字符为单位,依次移动模式串直到在某个位置发现匹配
蛮力匹配:版本1
- return i-j
i-j 大于n-m 即可判定失败。因为失败时 (字符串T)i=n,(模板串P)j<m。
i-j<=n-m 即可判定成功
i-j的意义是字符串中与模板串开始比较的位置。
蛮力匹配:版本2
上述算法有个细节
if( m <= j ) break;
直接跳出当前for(i。。。。i++)
的循环,而 当前循环的i
加1操作没有执行!
当返回值 i = n - m 时配对成功,当 i =n - m + 1 时配对失败
蛮力匹配:性能分析
- 最好最坏情况复杂度分析
- 最坏情况例子
字母表={0,1}
成功次数m-1次,失败次数1
特点
蛮力算法为何低效
- 有重复匹配的前缀:即一个字符串T中的一个位置需要比对多次。
- 不变性:模板P总是右移一位去比对。不会根据情况改变
KMP算法
next【】表
理解next【】表
理解N ( p , j )={ 0 <= t<j | P [ 0, t ) == P[ j-t , j ) };
- 具有特点:
快速右移
避免回溯
next【0】=-1
构造next【】表
next【j】的意思感觉下图说的不对,应该是最大自匹配的真前缀和真后缀的长度减1
- 当p【j】== p【 next [ j ] 】
计算next【j+1】
- 当p【j】!= p【 next [ j ] 】时
next【】表代码实现
KMP复杂度准确分析 ——线性时间O(n)
设一个k=2i-j (分析方法忽略吧)
KMP算法改进版
改进的原因:在当前模式串P的元素重复,使得连续与文本串T的元素进行对比失败,产生冗余,故可跳过相同元素与T的重复比对,提高KMP算法性能
BM_BC算法
动机——bc【】表
因为字符串配对过程中,大部分情况失败的概率远远大于成功的概率,故可采用bc表。next表善于利用配对成功的字符(经验),而bc表 注重配对失败的教训可以帮助我们排除更多字符。
坏字符
如何右移
试图从模式串P中找到一个X(与文本串T相同的X),使这个X能与T中的X对齐。P串偏移的距离存入bc【】表中。偏移距离如何确定
位移量取决于适配位置 j,以及X在模式串P中的秩,而与T和i无关。- 由此引申因偏移距离确定发生的三种情况
- 从模式串P中能找到一个或多个X(与文本串T相同的X) , 要位移量尽可能小,则要选择模式串P中X的 秩最大的(也可以说从最大秩开始 后面没有X了)且偏移量 j - bc [ ’ X ’ ] >0
- 从模式串P中不能找到一个X(与文本串T相同的X),则通过最左侧哨兵通配符" * ",将模式串P完整的移过X(文本串T中的X)这个位置。
- 虽然从模式串P找到X 但X过于靠右即秩过大,会造成偏移量 j - bc [ ’ X ’ ] <0 ,故只需将模式串P 向后一个位置。
- 由此引申因偏移距离确定发生的三种情况
构造bc【】
画家策略:模式串P中自左向右,每次出现对应的字符则更新最大秩
/*DSA*/#include "string_pm/string_pm_test.h"//*****************************************************************************************
// 0 bc['X'] m-1
// | | |
// ........................X***************************************
// .|<------------- 'X' free ------------>|
//*****************************************************************************************
int* buildBC ( char* P ) { //构造Bad Charactor Shift表:O(m + 256)int* bc = new int[256]; //BC表,与字符表等长for ( size_t j = 0; j < 256; j ++ ) bc[j] = -1; //初始化:首先假设所有字符均未在P中出现for ( size_t m = strlen ( P ), j = 0; j < m; j ++ ) //自左向右扫描模式串Pbc[ P[j] ] = j; //将字符P[j]的BC项更新为j(单调递增)——画家算法/*DSA*/printBC ( bc );return bc;
}
最好情况—— O(n/m)
在当前情况下,p一共移动 n/m次就停止,所以最好情况是 O(n/m)
最坏情况—— O(n*m)
因为p从最末尾开始
可以发现BM算法也并非完美,故将BM_BC+KMP算法结合则会产生完美的算法
BM_GS算法
好后缀策略
概念
实例
构造GS表
- 构造gs表的过程:MS【】——> ss【】——>gs【】
- MS【】的含义↓
注意3 和 4的含义。
“I C E”与后缀最长匹配者
ss【j】= MS【j】的长度= 3“RICE”与后缀最长匹配者
ss【j】= MS【j】的长度= 4
性能
注:n为文本串T的长度,m为模式串P的长度
蛮力算法BF:单次比对成功率越高其复杂度越高,最好O(n+m),最坏O(nm)
KMP算法:稳定一直保持线性时间复杂度O(n+m)
BM算法_BC:适合大字符集、单次比对失败率较高的情况,最好O(n/m),最坏O(nm)
BM算法_BC+GS:充分补偿了BC的缺陷。故最好是O(n/m),最坏是O(n+m)
Karp-Rabin 算法:串即是数
凡物皆数
任何串都可以用 素数序列转化为自然数 N 表示出来。
串亦是数
若视作自然数比对,只需O(1)时间。
数位溢出
70bit???????不懂
70位的128进制才能表示十个位的自然数。咋算的?
散列压缩
基本构思:通过对比压缩后的指纹确定匹配位置,故只需要O(1)时间比对
散列冲突
有散列就有概率发生冲突,即有两个自然数%M 得到的值相等。
因此经过hash()筛选之后,还需要进行严格比对,方可确定是否匹配。
离Karp-Rabin算法只剩最后一步。。。
快速指纹计算
Karp-Rabin代码解析参考:https://blog.csdn.net/Shine__Wong/article/details/102095474
代码涉及将串转为数且要除余,来限定范围。
邓俊辉 数据结构与算法C++版 第十三章 串 ADT相关推荐
- 邓俊辉数据结构与算法学习笔记-第十一章
文章目录 11.串 11.a ADT 11.b 串匹配 11.b1 串匹配 11.b2 蛮力匹配 11.c KMP算法 11.c1 KMP算法:从记忆力到预知力 11.c2 KMP算法查表 11.c3 ...
- 邓俊辉数据结构与算法学习笔记-第四章
文章目录 栈和队列 a 栈的接口与实现 a1 栈 a2 实例 a3 实现 c c1-1 栈的典型应用 c1-2 进制转换算法 c1-3实现 c2-1括号匹配实例 c2-2 尝试 c2-3 构思 c2- ...
- 清华大学邓俊辉-数据结构MOOC笔记-树的概念及逻辑表示
清华大学邓俊辉-数据结构MOOC笔记-树的概念及逻辑表示 有关概念: 与图论略有不同,数据结构中的树:1.需要为每一颗树指定一个特殊的顶点,作为"根"(root),对应rooted ...
- 邓俊辉数据结构学习心得系列——如何正确衡量一个算法的好坏
数据结构这门课主要关注如何设计合理的数据结构和算法,来简化时间复杂度和空间复杂度. 想要科学的解决这样一个优化的问题,最核心的思想也是最基础的,就是要量化问题.这也是将数学运用在实际问题中的一个基石. ...
- 邓俊辉数据结构学习心得系列——数据结构中所研究的算法
写在前面的话: 本文只是个人学习邓俊辉老师C++数据结构的整理,包含了很多个人的见解(从内容到材料的组织形式).所整理的内容不保证逻辑性和完整性,仅供参考. 算法的基本性质: 有正确的输入 有正确的输 ...
- 邓俊辉数据结构学习-3-栈
栈的学习 栈的应用场合 逆序输出 输出次序与处理过程颠倒,递归深度和输出长度不易预知 不是很理解 实例:进制转换 大致思路:对于进制转换,我们一般使用的都是长除法,因此要保存每次得到的余数,但是最后算 ...
- 邓俊辉数据结构学习笔记3-二叉树
二叉树及其表示 树 有根树 从图论的角度看,树等价于连通无环图.因此与一般的图相同,树也由一组项点〈vertex)以及联接与其间的若干条边〈edge) 组成.在计算机科学中,往往还会在此基础上,再指定 ...
- 邓俊辉数据结构学习笔记2
列表 typedef int Rank; //秩 #define ListNodePosi(T) ListNode<T>* //列表节点位置template<typename T&g ...
- 邓俊辉数据结构学习-7-BST
二叉搜索树(Binary-Search-Tree)--BST 要求:AVL树是BBST的一个种类,继承自BST,对于AVL树,不做太多掌握要求 四种旋转,旋转是BBST自平衡的基本,变换,主要掌握旋转 ...
最新文章
- C# Winform应用程序占用内存较大解决方法整理(转)
- 前端开发之JavaScript基础篇四
- ThinkPHP入门--后盾视频
- Vbox配置仅主机模式
- Android四大组件之BroadCast(续)
- 全国教学交流研讨会“教学为本”主题总结
- Flutter CupertinoSliverRefreshControl 苹果风格的刷新效果
- nginx动静分离配置_Nginx动静分离配置实例
- #分布式系统架构之# 事件驱动模式以及与之匹配的长时间处理过程讨论
- 团体程序设计天梯赛-练习集-L1-036. A乘以B
- python代码-在哪里编写python代码
- 基于AI分子力场模拟分子动力学
- 我在华为做外包的真实经历!
- DEL: 华为无线modem变无线路由器
- 反斜杆e,Linux下五彩斑斓的命令行输出
- 商品详情页商品属性选择,包含多规格
- 发布会签到系统_系统开发_创建项目及应用
- 信息与计算机,科学网—信息与计算机(1) - 姜咏江的博文
- Core Animation学习笔记—第二节Setting up Layer Objects
- 多重共线性是如何影响回归模型的
热门文章
- web集群之通过tomcat部署jpress应用
- 全球机场与航空公司准点率数据报告,为五一小长假做足准备
- 安徽阜阳计算机高中学校排名,安徽最强的五所高中,都是知名实力中学,考上就离名牌大学不远了!...
- scrapy爬取51job职位信息(针对2020.851job新的反爬虫机制)
- mysql leader/followers_Leader/Followers 模式
- yolo 深度学习_YoLo v1-v3深度学习网络-结构简介
- 论文笔记:3D-CVF(ECCV 2020)
- Win32创建菜单篇
- solidity msg.sender.transfer发送给谁
- Objective-C类别(catagory)