一、简答题:
1、extern “c”{}是什么含义?用来解决什么问题?
分析;extern "C" 包含双重含义,从字面上即可得到:首先,被它修饰的目标是“extern”的;其次,被它修饰的目标是“C”的。让我们来详细解读这两重含义。
extern “c”是指将该段代码以C语言形式进行编译、链接。由于C不支持函数重载,C与C++对于同一函数进行编译后在符号表中保存的函数名存在差异,故当进行C、C++混编时会出现一些问题。
单例模式 适配器模式 工厂模式 装饰模式
3、Tcp连接的time-wait是什么状态,描述其发生的场景,说明它存在的好处/坏处 。
分析:time_wait是TCP释放四次握手中的一个状态,当第三次握手完成时,即客户端收到来自服务器的FIN后,再发送一个ACK,客户便开始了time_wait状态。同时一个记时器开始记时,当达到2倍一个报文段在因特网中最大的生存期时代表超时。如果在超时前客户端再次收到FIN,则表示是服务器重发的FIN,客户端需重发送ACK。服务器在close socket之后便进入time_wait状态
算法设计与分析题
1、有N个任务(N < 1000),其中有些任务的执行依赖于其他任务的执行,如A任务执行之后B任务才能执行,但这些任务之间不存在循环依赖。请用一个算法来输出这些任务的执行顺序。
拓扑排序
算法思路:
1 把各个任务之间的依赖关系用有向无环图来表示,例如A任务依赖B任务,则建立一条B指向A的弧。(题目要求可以保证这个图无环)
2 计算有向无环图中各个节点的入度。
3 输出入度为0的节点,并删除该节点和所有以它为尾的弧。
4 重复第3步,直到所有节点都已输出。
5 输出的节点序列即为拓扑排序序列,也为任务的执行顺序。
值得注意的是,拓扑排序序列也可以用来验证各个任务间是否存在循环依赖,也就是有向图是否存在环。如果输出的拓扑排序序列中包含了所有的任务,则有向图肯定不存在环。
伪代码:
在实际的实现中,对于入度为0的节点,不需要真正删除节点以及所有以它为尾的弧,可以转换为对弧头节点入度减1操作。
//假设用邻接表存储有向图
status TopologicalSort(ALGraph G) { //对各个节点求入度,存储在indegree数组中 FindInDegree(G, indegree); //初始化栈 InitStack(S); //遍历所有节点,把入度为0的节点加入栈 for(i=0; i<G.vexnum; i++){ if(!indegree(i)) Push(S, i); } count = 0; while(!StackEmpty(S)){ //出栈并输入之 Pop(S, i); printf(i, G.vertices[i].data); count++; //对所有它的邻接点进行入度减一操作,如果入度减为0,则进栈 for(p=G.vertices[i].firstarc; p; p=p->nextarc){ k = p->adjvex; if(!--indegree[k]) Push(S, k); } } //判断所有的有向图节点是否在拓扑排序序列中,如果在,则有向图无环,否则有环 if(count < G.vexnum) return ERROR; else return OK; }
时间复杂度分析:
假设有n个节点,e条弧。求各个节点入度花费O(e),把入度为0的节点加入栈花费O(n),while循环中每次对入度减一的操作可以看作删除一条弧的操作,把所有弧删除完了,while循环也结束了,因此while循环花费O(e)。所以总的时间复杂度为O(n+e)。
2、查找一个文本内的完整句子的数量,文本中包含大小写字母、空格、“,”和“.”,完整的句子是指以“.”结束,且“.”号前必须出现至少一个字母。写出程序。
思路:读入文本每一行,然后遍历。
记录每一行最后一个字符,若行首为“.”,则需要上一行末尾的字符。
int count_prefect_sentence(string str) { int i = 0, cnt = 0, hasOneLetter = 0; while(str[i]) { if(str[i] == '.') { if(hasOneLetter) cnt++; hasOneLetter = 0; } else if(isalpha(str[i])) hasOneLetter = 1; i++; } return cnt; }
系统设计题
1、有1000亿条记录,每个记录包含url、ip、访问时间,请设计一个系统,满足下面两个查询:
1.针对特定的时间段(精确到分),计算访问特定url的ip数;
2.针对特定的时间段(精确到分),计算访问特定ip访问的url数。
映射Map[url][time],将url进行字符串hash,再进行枚举统计。
这两题如果做成两维映射,内存吃不消,既然两题中的一维是已经指定的,变化的只是时间段,因此可以用一维表示,先预处理,再进行统计。
用的MapReduce的思想。
按时间分成小文件,各自对url和ip进行hash。
再分级做桶,同时merge各时间区段的hash表。
这样查询就能做到Log级别。
2009百度实习生笔试题目
一、编程题(30分)
输入:N(整数)
输入:数据文件A.txt,不超过6条记录,字符串长度不超过15个字节
文件格式如下:
字符串\t数字\n
说明:
每行为1条记录;字符串中不含有\t。
数字描述的是该字符串的出现概率,小于等于100的整数。
多条记录的出现概率之和为100,如果A.txt不满足该条件,程序则退出;
如果文件格式错误,程序也退出。
要求:
编写一个程序,输入为N(正整数),读入文件A.txt,按照字符串出现概率随机
地输出字符串,输出N条记录
例如:
输入文件A.txt
abc\t20
a\t30
de\t50
输入为:10
即 abc有20%的概率输出,a有30%的概率输出,de有50%的概率输出,输出10条记
录
以下为一次输出的结果,多次输出的结果可能不相同。
abc
a
de
de
abc
de
a
de
a
de
二、算法题(35分)
题目描述:
设有n个正整数,将它们联接成一排,组成一个最小的多位整数。
程序输入:n个数
程序输出:联接成的多位数
例如:
n=2时,2个整数32,321连接成的最小整数为:32132,
n=4时,4个整数55,31,312, 33 联接成的最小整数为:312313355
[题目要求]
1. 给出伪代码即可,请给出对应的文字说明,并使用上面给出的例子试验你的算
法。
2. 给出算法的时间空间复杂度。
3. 证明你的算法。(非常重要)
三、系统设计题(35分)
在一个有1000万用户的系统中,设计一个推送(feed)系统。以下是一些预定义概
念
1、用户:在这个系统中,每个用户用一个递增的unsigned int来表示user id(简
写为uid);则uid的范围是从1到1000万的正整数。
2、好友:用户之间可以形成好友关系,好友是双向的;比如说uid为3和uid为4的
两个用户可以互为好友。每个用户好友的上限是500个;用户之间的好友关系可以
被解除
3、活动:每个用户只能发文章;文章可以被作者删除,其他人不能删除非自己发
表的文章;每篇文章通过一个blogid表示。
4、feed:我们希望,每个用户可以看到他所有好友的活动列表,在这个简化的系
统中就是所有好友的文章更新列表。
5、访问量要求:所有feed访问量每天在1亿量级;所有的blogid增加量每天在百
万量级。
题目:请在以上限制条件下,设计一个高效的feed访问系统。
要求:
1、能够尽快的返回每个用户的好友feed列表,每个用户可以最多保留1000条feed ;
feed的展现按照时间倒排序,最新的在最前面
2、用户删除某篇文章后,被推出去的feed需要及时消失。即每个用户看到的好友
feed都是未被删除的
3、尽可能高效。