基于位示图法的排序
@(算法学习)
–算法思路来自《编程珠玑》
文中提及这个算法的场景是对磁盘排序,1000万级别的数据量,虽然每条数据只有7B(Byte),总量却可以达到:7000万B,也就是差不多:8.3G的存储空间。现在看来(2016.11),计算机有8G以上内存的挺多了。但我的机器还跑不了,只有8G内存。所以,这种超过内存总量的排序就不可能一次性完成,需要分割归并。也就是读写磁盘不止一次,那么这样的算法将是非常非常慢的,I/O是最耗时的操作。
但是,如果用位示图的方式,问题将化为1~2MB的内存就能解决的问题。
但是前提是,数据没有重复。
基于位的操作,我们知道总是有意想不到的惊喜。这里也是。
1000万个数,用1000万位的字符串来表示,也就是1000万bits,也就约1.2MB,这是普通的计算机都能轻易搞定的。
简单说,就是用’0’或者’1’标记这个数是否存在。
比如:[1,4,2,7,8],最大的数是8,所以需要8位字符来标记:”011010011”就标记好了。
这样输出数据时,只需要看字符串中对应的字符是否为’1’,决定是不是输出即可。
这是一个对于不含重复数字很有效的排序策略。
#include <stdio.h>
char bits[10];
int nums[9] = {1,3,7,6,2,4,5,9,8};
int main()
{
//phase 1:
for(int i = 0; i < 10; i++)
{
bits[i] = '0';
}
// phase 2:
for(int i = 0; i < 10; i++)
{
bits[nums[i]] = '1';
}
//phase 3:
for(int i = 0; i < 10; i++)
{
if(bits[i] == '1')
{
printf("%d\n", i);
}
}
return 0;
}
时间效率是O(n),空间效率也是O(n),因此算是很高效的算法。