电面, 第一轮 :
Leetcode -> Game of life: 不需要in place的解法。 follow up 是 如果数据很大,内存存不下怎么办,需要写代码(可以自己假设已经存在文件读写的API)
电面, 第二轮 :
Leetcode -> Combination of phone number : 也是地里的面经题目。
onsite:
1. Remove Duplicate files 地里经典面经。
2. 实现一个网络爬虫,先写单线程的版本,然后是多线程的版本,注意多线程版本如何控制结束条件。
3. 系统设计twitter。 需要设计app 端和server端怎么交互。(问的很细)
4. 实现 read write lock。(面试官 用的是 mutex) --> follow up, 怎么优化锁,读操作和写操作很多的时候,怎么权衡。.
第一轮,三哥,game of life,写完后问矩阵很大怎么办,我说一行一行读,然后写了个一行行读读的代码,java写白板真是很慢。。。然后让算了下每次内存占用多少,然后问问题结束了。
第二轮白人,问了个分配id的问题,范围从1-n,写两个函数allocate和release。第二轮之前lz上了个厕所,然而不幸迷路,最终让前台MM带回,结果面试只有50min。lz和面试官讨论了一下,写了个N位bit的方法,写完还剩15min,白人让优化,但是说时间来不及了,你就说想法,然后就想到了用线段树的方法,讨论了下时间空间复杂度,期间让算了下内存占用,然后问问题结束。
最后一轮,真的是很累了。白人,本来又问了那个分配id的题,我说这题第二轮问过了,换了个bitTorent的题,第一问很常规,很快写出来了,分析了下复杂度,然后followup,很快又想出来了,但是让优化,没想出来,然后最后一看时间来不及了,匆忙写了下我那个方法,后来被告知要用平衡树。。。感觉这轮答的一般
一面:给一个文件和一个byte数组,判断这个byte数组是否在文件里出现过?本质是字符串匹配,然而不同的是文件可能很大,不能一次性读进内存。我是假设了一个常量表示了内存分配给我(要解释为什么需要这个常量),创建一段buffer,一开始将它填满,然后匹配buffer和byte数组(过程就和字符串匹配一样,我是用最蠢的办法),配不上的话,将最后的(byte数组长度-1)个byte移到buffer前端,然后继续读文件更新buffer剩下的部分,再次匹配,重复这个过程知道文件到尾或者匹配成功。写完后出了两个bug,在面试官提示下修复了,不是自己找出来的= = 然后是followup,提高时间效率,我说用KMP?他说我不期望你用KMP,那是有点research的方法。我又想了一下,他给我hint说你知道rollinghash吗?我说不知道= =他就跟我简单解释了一下,就是一个byte数组有一个hash值,然后当删除一个前端的byte或者添加一个新的byte在末尾的时候,可以通过运算在O(1)时间内算出新的hash值。然后就给我一个class rollinghash,三个方法addbyte,removebyte,hash,叫我根据这个改代码。改完之后(这一次应该没有bug了= =),他问我有什么好方法可以实现这个hash函数吗(要求当然就是rollinghash这个类里的三个方法都是常数复杂度),不要求unique,但尽量要求不同?我说XOR每个byte?每个byte相加?他说可以,然后他说了一个他们在用的办法:设一个常数a,假设byte数组是bytes[0:n-1],那么hash值为a^(n-1)*byte[n-1]+a^(n-2)*byte[n-2]+...+a^0*byte[0]
二面:经典买soda题,用dfs,要求改进,用dp,然后分析两者复杂度。做的时候太困,傻不拉几的,建议大家吃完午饭后喝咖啡。。当然因人而异哈
三面:二面之后喝了咖啡,复活了。实现一个分配id的类,id可以是0~MAX_ID-1中的一个值,分配出去的id必须唯一,类里面还有个回收id的函数,总而言之就是实现这个类的两个函数allocate和dellocate,数组结构自己设计。我说了两个方案,一个用queue,一个用bool数组。他让我先讨论用queue的情况,写了代码,用queue很直接,然后他让改进时间和空间,方案就是用一个自增的整数,表示还没被分配的id,初始化为0,再有一个队列,每当dellocate时,就将这个回收的id放到一个队列里。每当allocate时,先判断这个队列里有没有id,有的话拿出来返回,没有就拿那个整数,并另其+=1,这样的话构造函数的复杂度就变成O(1)了,同时空间也省了很多。接着让讨论bool数组的情况,这个方法比较糟糕,初始化O(n),allocateO(n),唯一好处就是空间比queue省一点。然后他让改进,想了一会无果,他提示有没有办法可以让allocate更快呢,快32倍,快64倍。然后我就说用bit,每次我可以扫32位(int),然后如果这个int大于0的话,就说明这里面有一个id可用,然后就可以用常数级的方法找出这个id。他说还有没有更快的,比如存储一些临时信息?我就基于前面的方法和这个hint想到了用线段树,这样的话,初始化O(n),allocateO(logn),dellocateO(logn),然后他让我写了代码,假设线段树已经建好了,要我实现allocate函数,pls note that 在实现的过程中,我假设一个数节点存着区间开始和结束点,可用id数量,左孩子和右孩子指针。写完后他让我优化空间,我说不需要开始和结束点,因为可以通过计算算出来。让我再优化,我说可用id数量可以换成一个bool值。让我再优化,让我省去两个指针,我说或许我可以用堆的数组实现方式来做,但是这不一定是一颗满二叉树,他说那假设maxid是2^n吧,我说那可以了,我只用一个数组就好了,a的左右孩子分别为a[2i+1],a[2i+2]。然后最终方案就变成了只需要2*MAX_ID-1个bit的空间来实现。总结一下就是用queue耗空间省时间,数组耗时间省空间。
1. id allocation/deallocation 先實作了queue的做法, 然後是bit array, 問是否有time/space complexity在兩個之間的方法。最後作了binary tree (each node stores whether there‘s any available ids in its subtrees) 有寫完,面試官很滿意
2. download bit-torrent. 第一題基本上就是merge intervals。後來是interval連續進入,寫了一個binary search找位置然後linear update. 寫完後考慮要問演算法(猜測是用樹來解這題)或是system,選了system.結果問如果真的download這些paritial file後要怎麼merge real files
3. Sharpness value. 一開始以為是新題,說要在一個image中找最像地平線的一條線。DP解。問如果圖太大怎麼處理,問各種讀法的disk access次數。期待的答案好像是把各種讀法的disk access次數寫成一個function然後找到最佳解
4. Behavior
5. Project deep dive
6. 照片每次被view就會call View(photo id), 給top-k view photo. 一開始假設有整個oracle, 用heap解決。延伸如果view是一個個來,寫了一個很複雜的heap + hashmap。期待的最佳解應該是bucket sort
第一轮coding:Allocate IDs 经典老题,给出三种解法,面试官很满意
第二轮deep dive:毕竟工作四年多了,这轮发挥正常,把之前做的project挑出几个方面讲一讲
第三轮lunch:跟一个ABC小哥,聊的很愉快
第四轮coding: Web crawler + 多线程版。也是面经原题,就是吃完饭有点儿困,被找出来俩bug。。。. 1point 3acres 璁哄潧
第五轮All rounds:就是behavior questions,各种问平时工作中的困难啊,交流啊,什么情况应该怎么办啊。面试感觉中规中矩。
第六轮architecture: 设计一个upload file 到S3 还要通过thumbnail server把这个file做thumbnail的系统。我面完就觉得可能要跪在这一轮了,面试官问的非常非常仔细,各种某一部分down了应该怎么办啊,怎么提高用户体验啦之类的。。。。尽力答了,但是到最后有俩模块的处理还没答完。
.1. Game of lives, 输入: 给一个matrix的grid, 每个的值是Live or Dead, 输出: 一个同样大小的matrix, 每个的值设定如下:
如果目前值是live, 而且周围8个grid中, live的数量是2 or 3, 则变成dead. more info on 1point3acres.com
如果目前值是dead, 周围8个grid中, live数量是3, 变成live
followup: 尽量减少内存开销, 该怎么做.
2. 见过: 买罐装汽水,只能一罐一罐或者一箱一箱地买。箱子有几种不同大小,比如一箱12罐,一箱6罐, 一箱2, 一箱1 等等。这个input是个list。让输出所有买法(就是每种package买几个这样)
用recursive解了
followup: 如果剪纸
3. 老题目: 返回一个文件系统里面的duplicate files
4. 老题目: 设计一个web crawler, 多线程版本
5. 给出一堆log, 里面有photo id和访问时间, 还有一个iterator, 能够按照photoId 和访问时间iterate, 问如何输出top m的访问photo
followup: 如何存储这些log, 来支持方便的retrieve 这些信息.
6. Project deep dive.
7. Behavior questions, hard project, motivation, blablabla...