笔试相关3

  1. 单向循环链表,从头开始报数,报道m或其倍数时,出列,按照出列的先后顺序从新组织单链表

       函数原型为: void convert(Node**head,int m);

         解析:约瑟夫环的形式。head为二级指针,是重新组织后的循环单链表的表头。

 1 void KickFromRing(RingNodePtr pHead, int m)
 2 {
 3       RingNodePtr pCurr, pPrev;
 4       int i = 1;    // 计数
 5       pCurr = pPrev = pHead;
 6       while(pCurr != NULL)
 7       {
 8           if (i == m)
 9           {
10               // 踢出环
11               printf("\n%d", pCurr->pos);    // 显示出圈循序
12               pPrev->next = pCurr->next;
13               free(pCurr);
14               pCurr = pPrev->next;
15               i = 1;
16           }
17           pPrev = pCurr;
18           pCurr = pCurr->next;
19           if (pPrev == pCurr)
20           {
21               // 最后一个
22               printf("\n%d", pCurr->pos);    // 显示出圈循序
23               free(pCurr);
24               break;
25           }
26           i++;
27       }
28   }

2. 海量数据Top100

        a.一天的优酷视频播放量约1亿,视频总数约有100w。ID号是一个大小为20字节的字符串。如何求出当天播放视频的Top100

          可抽象为一个大文件,每行一个ID号,代表被播放的视频id。机器的内存不超过1G,如何抽取TOP100.先写思路,然后写程序。

        b.同样一个月的视频播放量约100亿。求出当月的视频播放top100,每台机器的内存不超过1G.描述所有可能的解决方案。

  解析:海量数据的处理。无法一次性装入内存,可先hash之分为多个文件处理,堆或者Trie树统计次数,求出每个文件中的Top 100。归并之求出总的top 100

  对于第二问:还可以hadoop mapReduce处理之。

  首先统计每个视频被观看次数,得到<id, cnt>键值对,其中id为视频id,cnt为视频被观看次数。 
  以cnt作为关键字建立最小堆。遍历所有键值对,若堆的size小于100,则将键值对直接插入堆,否则比较键值对和堆顶元素大小,若cnt大于堆顶元素的cnt,则弹  出堆顶元素并将键值对插入堆。 
  对于第一问,由于id个数较少,统计部分可直接使用stl的map容器。 
  对于第二问,由于id个数太大,直接hash内存不够,需要map&reduce。

3. 1-n中找缺失的数字,有n-1个数字,每一个都位于1-n之间,但是之中缺失了一个数字,要求找出这个缺失的数字,线性时间复杂度

         解析:异或。原理:相同的数异或为0,0与其他数异或结果为该数。

posted @ 2012-09-25 17:18  Michael020  阅读(162)  评论(0编辑  收藏  举报