部分题目整理:大数据

大数据的题目之所以难解,主要是因为我们日常所写的算法没有考虑内存不足的情况(事实上也很少见到),下面的题目都是我同学在前几个月的面试中或笔试中碰到的,在这里与大家分享。

1)给⼀一个超过100G⼤大⼩小的log file, log中存着IP地址, 设计算法找到出现次数最多的IP地址?!

很明显,你无法提供一个有100多G的内存的计算机,所以我们不能简单用平常的思路比如把数据放在一个顺序表里然后遍历。
在这里我们就要分批/区处理这些数据,假设我们把它分成1000分(或更多)存在硬盘里,那么每份平均大小约为100M,这样我们就可以在内存里依次遍历每份文件,我们可以找出每份文件里出现的最大次数的Ip地址,遍历完1000份文件后,在进行1000次比较即可。
思路大概是这样,但是细节上的问题我们没有解决,比如我们应该如何将原始数据划分为1000个文件?
我们可以划分区域,比如ip在0000到0010之间的在0号文件,到考虑到ip地址长度不同等问题很难实现;
并且要想实现上面的思路我们至少必须保证所有相同的ip应该都出现在一个文件里,要是对原文件依次比较遍历再存入对应文件,基本是不现实的。

在这里我们需要用到哈希表的思想。

这里写图片描述

那么我们还要做的就是用一个数组来保存每个文件出现次数最多的ip的以及出现次数,在进行比较即可。

2)与上题条件相同,如何找到top K的IP?

我们只需要再加入一个最小堆即可,我们运用上面的解法再加入最小堆,可以找到每个文件的top K ,然后再次使用一次最小堆找到整个数据的top K,如果你担心K较大导致所有文件的top K 内存可能不够,你可以放入硬盘依次读取。

3)给定100亿个整数,设计算法找到只出现⼀一次的
整数!

如果我们用4个字节来保存数据,需要内存大小为100亿4/1024 1024 * 1024 大约为10TB大小的内存,这显然不能一次性的在内存中解决。
我们可以用上面的思路用哈希表把原始数据分成足够小的文件再来判断只出现一次的数,时间复杂度为o(n*n),这是个很糟糕的情况,然而更糟糕的是n为100亿。。。
不知你是否想到了位图,没错我们可以用一个位来表示该数,比如第2000位就代表2000,然而1位只能表示这个数的2个状态,我们可以用2个字节即00:不存在,01:出现一次,11:出现次数>1.
这样我们需要的内存为42亿*2/1024*1024*1024(假设都为int),大约为8G,还是很大。这里我们就需要分批/区处理,将它分成若干个小文件依次进行处理。至于怎么划分,因为位图表示的数都是连续的,为了把空间利用率达到最高,我们为每个文件设置范围,这样在一个范围的数都在一个文件里。

这里写图片描述

这里还有一个问题,有负数怎么办?我们可以用2个位图来解决,一个是储存正数,一个为负数,你可以再把范围减少一半,这样每次遍历依然只消耗1G内存。
下来我们做的就是遍历所有文件来找到这个数。

4)给两个⽂文件,分别有100亿个整数,我们只有1G内存,如何找到两个⽂文件交集!

设2个文件为A和B.
我们可以对其中一个文件A进行一次哈希划分,把它分成若干个文件,在依次读取并遍历在硬盘保存的B,依次比较即可,这样的时间复杂度为o(n * n).
我们的时间复杂度并不是很理想,我们可以对A,B都进行哈希划分。
这里写图片描述

这样我们每次只遍历号数相同的文件即可,时间复杂度为o(n).

5)1个⽂件有100亿个int,1G内存,设计算法找到出现次数不超过2次的所有整数!

我们依旧用位图,用2个字节来表示一个数的状态,00:不存在。 01:出现一次。 10:出现2次。 11:出现次数>2次。剩下的与第二题相似,这里不再赘述。

6)给两个⽂文件,分别有100亿个query,我们只有1G内存,如何找到两个⽂文件交集?分别给出精确 算法和近似算法!

与第4题一样,这是精确算法。
另一种算法为布隆过滤器,我们先遍历A文件,构建布隆过滤器,然后再遍历B文件,过滤掉存在的query,。这种算法比精确算法快,但由于哈希冲突的原因, 只是一种近似算法。
布隆过滤器;
http://blog.csdn.net/fengasdfgh/article/details/53108263

7)如何扩展BloomFilter使得它⽀支持删除元素的操作?!
8)如何扩展BloomFilter使得它⽀支持计数操作?!

第7,8题我在布隆过滤器中也讲到了。链接:
http://blog.csdn.net/fengasdfgh/article/details/53108263

9)给上千个⽂文件,每个⽂文件⼤大⼩小为1K—100M。给n个词,设计算法对每个词找到所有包含它的⽂文 件,你只有100K内存!

与第6题相同,我们依次遍历所有存在硬盘里的文件,每次都重构一次布隆过滤器,再遍历储存词的文件,过滤出现的词,并且把文件名储存在相应的文件(包含所有包含这个词的头文件名,这个文件名你可以以单词+特殊字符命名)中。
这样每次占用内存的只有布隆过滤器,我们完全可以控制它的大小不超过100K。时间复杂度为o(m+n),m为文件个数。
上面得算法依旧只是近似算法,如果要精确地话,我们只能每次从头文件取值依次比较。时间复杂度为o(m+n),但如果算上字符串比较的次数,显然布隆过滤器耗时更少。

其实从上面的题可以看出,大数据更考验的是我们对数据结构的掌握程度,希望大家对数据结构有足够的重视。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值