1.【hash分治+图/小顶堆】将某天访问某url的次数最多的IP提取出来。
IP最多有2^32种,可以将其对1000取余,映射为1000个小文件,再找出每个文件中出现次数最多的IP(可以使用hash-map等),再从这1000个IP中找到最多的那个即可。
2.【hash分治+字典树】有1G大小文件,里面每行存一个单词小于16K,内存限制为1M,找出频率最高的100个单词。
将1G的文件对5000取模,每个文件约为200k,若大于1M,继续取模直到小于1M。
对每个小文件好似用字典树(tire树)进行查找重复最多的100个单词及频数并存入文件。
之后对这5000个文件进行归并排序即可。
其中用到了胜者树理论,关于胜者树与败者树详见:胜者树与败者树
3.【Bitmap】在2.5亿个整数中找出不重复的整数(内存不足以全部容纳所有整数)。
使用2-bitmap(每个数分配2bit,00表示不存在,01表示出现一次,10表示出现多次)。共需内存2^32*2bit=2GB内存。
扫描所有整数进2-bitmap,查看bitmap,输出所有标记01的整数。
4.【字典树】给40亿个不重复的unsigned int的整数,未排序。再给定一个整数,如何快速判该数是否在那40亿个数中?
因为2^32大于40亿,所以将所有40亿个数以32位二进制表示,并构建字典树。
并将给定的的整数也以32位二进制表示,在字典树中进行查找。时间复杂度为O(logn)。
5.【小顶堆】从100w个数中找出最大的100个数。
维护一个含有100个元素的最小堆,复杂度为O(100w*log100)。
其他思路:【快速排序】使用快速排序并只考虑比key大的部分,直到接近100时,使用传统排序取出前100个元素。
6.【二叉树】在大量游戏玩家中快速找到某个玩家的排名。
将所有玩家的成绩维护成一个二叉树,所有结点保存其左子树中包含结点的数量(left_points)。
计算查找该结点经过路径时所有右拐结点和本身的left_points之和即可。
持续更新中.....
1、几种进程间的通信方式
管道( pipe ):管道是一种半双工的通信方式,数据只能单向流动,而且只能在具有亲缘关系的进程间使用。进程的亲缘关系通常是指父子进程关系。
有名管道 (named pipe) : 有名管道也是半双工的通信方式,但是它允许无亲缘关系进程间的通信。
信号量( semophore ) : 信号量是一个计数器,可以用来控制多个进程对共享资源的访问。它常作为一种锁机制,防止某进程正在访问共享资源时,其他进程也访问该资源。因此,主要作为进程间以及同一进程内不同线程之间的同步手段。
消息队列( message queue ) : 消息队列是由消息的链表,存放在内核中并由消息队列标识符标识。消息队列克服了信号传递信息少、管道只能承载无格式字节流以及缓冲区大小受限等缺点。
信号 ( sinal ) : 信号是一种比较复杂的通信方式,用于通知接收进程某个事件已经发生。
共享内存( shared memory ) :共享内存就是映射一段能被其他进程所访问的内存,这段共享内存由一个进程创建,但多个进程都可以访问。共享内存是最快的 IPC 方式,它是针对其他进程间通信方式运行效率低而专门设计的。它往往与其他通信机制,如信号两,配合使用,来实现进程间的同步和通信。
套接字( socket ) : 套解口也是一种进程间通信机制,与其他通信机制不同的是,它可用于不同及其间的进程通信。