后缀数组

顾名思义。SuffixArray(下面有时简称SA) 和字符串的后缀有关。



后缀:字符串中某个位置一直到结尾的子串。(SA中讨论包含了原串和空串)。所以共同拥有len+1个后缀。



后缀数组: 字符串的全部后缀组成的按字典序从小到大排好的数组。因为SA中记录的都是字符串的后缀,所以SA仅仅须要记录其表示的后缀的起始位置。



因为比較字典序是O(n)的,所以暴力算法的复杂度将是O(n^2logn)。通过一些算法能够降到线性复杂度。这里先介绍一种简单的O(nlognlogn)的算法。

该算法的思想是通过倍增法减少了比較字典序的大小的复杂度O(n)到O(logn)。

其求解时不先算后缀,而是先算长度为1的子串的字典序大小排列,然后得到一个rank数组,即该子串在全部子串中排位的值。字典序越小,rank值越小。

rank[k][i] 表示起始位置为i的长度为k的子串在全部长度为k的子串中的字典序大小。

这时我们要比較长度为2k的子串的大小的话。其第i个位置的长度为2k的子串的大小能够通过比較rank[k][i]和rank[k][i+k]来实现。

SA中的sa[i]表示字典序位i的后缀串的起始位置。

const int MAXN = 100000 + 5;
int _k, _len;
int _rank[MAXN];
int _tmp[MAXN];
int _sa[MAXN];// 后缀数组。 bool _cmp(int i, int j) {
if (_rank[i] == _rank[j]) {
int _ri = (i+_k <= _len) ? _rank[i+_k] : -1;
int _rj = (j+_k <= _len) ? _rank[j+_k] : -1;
return _ri < _rj;
} else {
return _rank[i] < _rank[j];
}
} void Suffix_sa(string s, int* sa) {
_len = s.size(); for (int i=0; i<_len; i++) {
sa[i] = i;
_rank[i] = s[i];
}
sa[_len] = _len;
_rank[_len] = -1; for ( _k=1; _k<=_len; _k<<=1) {
sort(sa, sa+_len+1, _cmp); _tmp[sa[0]] = 0; for (int i=1; i<=_len; i++) {
_tmp[sa[i]] = _tmp[sa[i-1]];
if (_cmp(sa[i-1], sa[i])) {
_tmp[sa[i]]++;
}
} copy(_tmp, _tmp+_len+1, _rank);
}
}

Suffix Array 后缀数组的更多相关文章

  1. suffix array后缀数组

    倍增算法 基本定义子串:字符串 S 的子串 r[i..j],i≤j,表示 r 串中从 i 到 j 这一段也就是顺次排列 r[i],r[i+1],...,r[j]形成的字符串. 后缀:后缀是指从某个位置 ...

  2. bzoj 4319: Suffix reconstruction 后缀数组+构造

    题目大意 给定后缀数组sa,要求构造出满足sa数组的字符串.或输出无解\(n\leq 5*10^5\) 题解 我们按照字典序来考虑每个后缀 对于\(Suffix(sa[i])\)和\(Suffix(s ...

  3. BZOJ 4319: cerc2008 Suffix reconstruction(后缀数组)

    题面 Description 话说练习后缀数组时,小C 刷遍 poj 后缀数组题, 各类字符串题闻之丧胆.就在准备对敌方武将发出连环杀时,对方一记无中生有,又一招顺 手牵羊,小C 程序中的原字符数组就 ...

  4. BZOJ.4319.[cerc2008]Suffix reconstruction(后缀数组 构造 贪心)

    题目链接 \(Description\) 给定SA数组,求满足SA[]的一个原字符串(每个字符为小写字母),无解输出-1. \(Solution\) 假设我们现在有suf(SA[j]),要构造suf( ...

  5. 后缀数组(suffix array)

    参考: Suffix array - Wiki 后缀数组(suffix array)详解 6.3   Suffix Arrays - 算法红宝书 Suffix Array 后缀数组 基本概念 应用:字 ...

  6. 后缀数组(suffix array)详解

    写在前面 在字符串处理当中,后缀树和后缀数组都是非常有力的工具. 其中后缀树大家了解得比较多,关于后缀数组则很少见于国内的资料. 其实后缀数组是后缀树的一个非常精巧的替代品,它比后缀树容易编程实现, ...

  7. 利用后缀数组(suffix array)求最长公共子串(longest common substring)

    摘要:本文讨论了最长公共子串的的相关算法的时间复杂度,然后在后缀数组的基础上提出了一个时间复杂度为o(n^2*logn),空间复杂度为o(n)的算法.该算法虽然不及动态规划和后缀树算法的复杂度低,但其 ...

  8. 笔试算法题(40):后缀数组 & 后缀树(Suffix Array & Suffix Tree)

    议题:后缀数组(Suffix Array) 分析: 后缀树和后缀数组都是处理字符串的有效工具,前者较为常见,但后者更容易编程实现,空间耗用更少:后缀数组可用于解决最长公共子串问题,多模式匹配问题,最长 ...

  9. 数据结构之后缀数组suffix array

    在字符串处理当中,后缀树和后缀数组都是非常有力的工具,其中后缀树大家了解得比较多,关于后缀数组则很少见于国内的资料.其实后缀是后缀树的一个非常精巧的替代品,它比后缀树容易编程实现,能够实现后缀树的很多 ...

随机推荐

  1. [源码管理] ubuntu下SVN服务器安装配置

    一.SVN安装1.安装包$ sudo apt-get install subversion2.添加svn管理用户及subversion组$ sudo adduser svnuser$ sudo add ...

  2. c.vim的安装和使用

    之前写了一些废话,今天写的稍微具体点. 在mac上给vim装个插件,,倒腾了半天 先要去找到c.vim.zip,自己百度下,官网就有的,我mac下下来,是直接解压的格式,而不是*.zip,也就是说不需 ...

  3. mvc 伪静态任意扩展名的实现方法

    比如:要实现 http://localhost:60291/home/geta/1212.html 或者 .abc 任意扩展名 完成两步即可. 第一步修改路由: public static void ...

  4. DataTable和List相互转换的类

    DataTable与List相互转换 .NET后台数据处理,从数据库中的捞出的数据格式一般是List和DataTable的格式.现在将两种格式相互转换的心得记录下来以便以后查找(直接上代码). pub ...

  5. 异步lambda表达式

  6. mybatis学习笔记之基础框架(2)

    mybatis学习笔记之基础框架(2) mybatis是一个持久层的框架,是apache下的顶级项目. mybatis让程序将主要精力放在sql上,通过mybatis提供的映射方式,自由灵活生成满足s ...

  7. hdu2853 Assignment 完美匹配 多校联赛的好题

    PS:好题.不看题解绝对AC不了. 题解来源: http://blog.csdn.net/niushuai666/article/details/7176290 http://www.cnblogs. ...

  8. APP开发中,如何从UI设计上提升APP用户体验

    设计中有很多细微的东西要注意,就如UI设计中,元素的统一性,图标风格.段落的排版等等,只有能注意这些细节,你的 APP UI 才算合格. 干货君总结了17个提升用户体验的 UI 设计小技巧,也是我们日 ...

  9. 03--实例讲解虚拟机3种网络模式(桥接、nat、Host-only)

    前言 很多人安装虚拟机的时候,经常遇到不能上网的问题,而vmware有三种网络模式,对初学者来说也比较眼花聊乱,今天我就来基于虚拟机3种网络模式,帮大家普及下虚拟机上网的背景知识.(博文原创自http ...

  10. HTML 单击a标签 实现下载文件而不是浏览器打开预览

    <a d ownload class="down" title="">