这是C++算法基础-基础算法专栏的第十七篇文章,专栏详情请见此处。
引入
在一些题目中,有些数据因为本身很大或者类型不支持,自身无法作为数组的下标来方便地处理,但是影响最终结果的只有元素之间的相对大小关系,这时,我们可以将原来的数据按照排名来处理问题,即离散化。
下面我们就来讲离散化的实现。
定义
离散化是一种数据处理的技巧,本质上可以看成是一种哈希,其保证数据在哈希以后仍然保持原来的顺序。
Q:什么是哈希?
A:哈希是将输入映射到一个值域较小、可以方便比较的范围。
过程
将一个数组离散化,并进行查询是比较常用的应用场景。
最常见的离散化是:通常原数组中有重复的元素,需要把相同的元素离散化为相同的数据。
方法如下:
-
复制一份原数组的副本。
-
将副本中的值从小到大排序。
-
将排序好的副本去重。
-
查找原数组的每一个元素在副本中的位置,位置即为排名,将其作为离散化后的值。
其中,第二步可以用排序sort()函数实现,第三步可以用去重unique()函数实现,第四步可以用二分查找lower_bound()函数实现,这三个函数都是C++STL中的函数,头文件为<algorithm>。
性质
时间复杂度
复制复杂度为,排序复杂度为
,去重复杂度为
,最后的
次查找复杂度为
。综上,总时间复杂度为
。
空间复杂度
空间复杂度为。
代码
下面给出离散化的实现代码:
for(int i=1;i<=n;i++) //step1
tmp[i]=arr[i];
sort(tmp+1,tmp+n+1); //step2
int len=unique(tmp+1,tmp+n+1)-(tmp+1); //step3
for(int i=1;i<=n;i++) //step4
arr[i]=lower_bound(tmp+1,tmp+len+1,arr[i])-tmp;
代码解释
代码中的step1~4分别对应过程中的四个步骤。
上一篇-位运算的实现 C++算法基础专栏文章 下一篇-区间合并问题的实现
每周六更新一篇文章,内容一般是自己总结的经验或是在其他网站上整理的优质内容
点个赞,关注一下呗~