点击上方“程序员大咖”,选择“置顶公众号”
关键时刻,第一时间送达!
对于那些即将开始找工作的人来说,如果你没有诸如斯坦福大学这样的名校计算机学位,那么你可能会担心自己无法获得顶尖科技公司的工作机会。也许身边有人告诉你,以你的资历不足以在微软或者 Facebook 这样的公司找到工作。但本文的作者用自己的切身经验表示,你可以。
本文将分享作者在Facebook、谷歌、亚马逊、LinkedIn、微软、Twitter、Pinterest、Snapchat 等顶级科技公司的面试经历,讲述他是如何获得多个科技公司的 Offer,并最终在 Twitter 获得梦寐以求的工作的。
个人背景
我的大学很普通,并没有藤校光环。我在爱达荷州的一所社区学院学习了两年,然后在一所天主教大学获得了计算机学位。
兴趣使然,我在大学三年级时开始学习计算机科学。当时我唯一拥有的类似电脑的东西就是中国版的山寨任天堂 SNES 。当我把磁带放进去时,它老是出问题。
为了在大学期间自己养活自己,我不得不做多份兼职。
毕业时我开始找正式的工作,我采用广撒网的策略,向多个知名科技公司都投递了申请,并且有幸得到了几次电话面试的机会。
最初自己缺乏面试经验,自认为面试官会问一些链表或者二叉树之类的问题。然后实际并非如此,因此我面试失败了。
勇往直前
我没有过多地探究自己是否优秀。我知道自己的学习能力非常强,我需要的只是一个机会。
正如大家所说的那样,要广撒网。而我也正是这样做的。
我接下来做了一件非常引以为傲的事情。我编写了一个简单的 Python 脚本,它可以从Craigslist 上自动抓取一些含有关键字的职位列表,并将这些职位对应的邮件联系方式存到电子表格中。
这并不是最聪明的解决办法,但在 Craigslist 上发帖的人对他们所要招聘职位的描述出奇地准确。
然而,Craigslist 并不喜欢人们抓取他们网站上的内容。为了解决这个问题,我通过一个 VPN 运行我的脚本,并利用定时器每隔几分钟就暂停脚本。虽然它并不完美,但运行情况也还可以。
最后,我搜集了来自旧金山、波特兰、斯波坎和西雅图的大约500个公司的招聘电子邮件。我根据这些职位的具体发布时间和其它信息对结果进行了过滤,并通过添加越来越多的特性来改进它。
后来我发现已经有一些脚本在爬取 Craigslist 上的信息并自动发送电子邮件。这些大多是海外公司,它们希望把自己推销到美国市场。
我采用了一个变通方法,我精心制作了电子邮件,我在邮件标题里使用了那些公司发布的招聘信息里的一些关键词。然后,我在邮件正文部分添加了更多的细节信息,让邮件内容看起来更加个性化,不像是模板。我做了一个快速的A/B测试,就这样,我收到的应聘公司的回复率从2-3%增加到了10%。
在发送的大约500封应聘电子邮件中,我收到了大约50份回复,其中一小部分给了我电话面试的机会。我之所以只发500封电子邮件,这是因为我时间不够,我需要尽快找到一份工作。我需要尽可能地提高面试通过率,而不是获得尽可能多的面试机会。
幸运的是,我最终在西雅图的一家创业公司找到了一份初级软件工程师的工作。这家创业公司当时位于 Kirkland,所以我必须坐45分钟的巴士才能赶上面试的时间。
接下来我在这家公司工作了3年半。我在那里学到了很多东西,比如亚马逊 AWS、EC2、DynamoDB、SQS 和 Docker。我在这段时间里成长了很多,我学习了如何编写模块化的、可维护的代码,我学会了如何进行软件设计,我也学会了如何处理人事方面的问题。
我所在的团队成员大都是行业佼佼者,他们都曾供职过很多知名公司,比如微软、亚马逊、LinkedIn。我把自己定位成一块“海绵”,尽情地从他们身上进行吸收和学习,这对我的职业生涯产生了非常巨大的影响。
初创公司的日子
我在加入的第一家创业公司工作期间,所做的几乎全部都是后台开发方面的工作,中间会涉及一些开发运维。我开始编写一些函数来添加或修改一个影响范围很小的特性,不过这是一个了解代码库并进行一些代码审查的好机会。
一年之后,我开始负责代码库的一部分,然后我的任务是将一组特性转换为服务。这是这家创业公司 SOA 阶段的开始。我们开始将站点的各种组件转换为服务,我就是在这个过程中学习了更多有关 RESTful 服务、身份验证、AWS 服务、发布/订阅、分布式系统等方面的知识的。
有趣的是,我并不是通过书本或正规的教育来学习这些知识的。相反,是因为我在实际工作中需要开发完成一系列功能部件,但我在这方面存在知识瓶颈。
所以我想,那就边学边做吧。
很多时候,我都陷入了分析瘫痪状态,在这种状态下,我过度分析了各种情形场景,最终无法取得进展。
那些艰难的时刻其实是最好的学习机会。我开始学习功能范围、监视、警报和文档方面的知识。这个过程的每一步都揭示出我需要学习更多的东西。不管是作为一个普通人还是软件工程师,过去2到3年都是我人生中成长最快的时期。
我如何准备面试
在经历了第一次求职面试中的各种艰难曲折后,我告诉自己,在未来的求职面试中我必须做好充足的准备。
我对自己擅长的、不擅长的以及可以改进的地方进行总结,从而为未来的面试做好充分准备。我将它分为三个类别:数据结构、算法和系统设计。
我的正式职业生涯的编程语言基本都是 PHP ,在大学里也学过 C++,所以我想尝试一些更简单、更不繁琐的面试。因为这个原因,我选择了Python。这是一门非常强大的语言,并且易于学习,支持许多开箱即用的数据结构,并且可以在白板上快速书写。我是通过 Youtube 上的一些视频教程学习 Python 的,此外还阅读了教学文档。我选择学习 Python 的另一个原因是,它具有很高的可读性,而且在白板上书写很容易。
首先是用 C++ 语言写的降序排序:
#include <bits/stdc++.h>
using namespace std;
int main()
{
int arr[] = {1,10,0,4,5}
int n = size(arr)/sizeof(arr[0]);
sort(arr, arr + n, greater<int>());
for (int i = 0; i < n; i++) {
cout << arr[i] << " ";
}
return 0;
}
以下代码是 C++ 和 Python 之间的一个简单的比较:
a = [1,2,4,5,1000]
a.sort(reverse=True)
print a
我积累的经验的是,很多应聘者在面试过程中会在简洁方面犯错。在45分钟的面试中,你需要用大部分的时间来解决实际问题。
吐血建议:选择一种简洁的编程语言,这样你就可以在白板上更快地写代码。
面试准备模式
我花了大约一个星期的时间在 LeetCode、HackerRank 和 Project Euler 中做了一些简单的测试,以便熟悉它们的接口,并让自己开始习惯使用 Python 编写代码。
第一周我对自己在某些编程语言方面的能力水平进行了摸底。我又花了一周时间来进行一些设计上的准备,并尽可能做到深入和广泛。
这对我来说是非常有趣的,因为我经常查看 iOS 应用,并试图弄清楚它们是如何开发出来的。例如,如何从头开始开发 Instagram?(我在 Facebook 面试时曾被问到这个问题)。
我的专业背景是 API 设计和服务导向式架构。因此,我借此机会展示了我将如何设计自己的 Instagram 版本。因为我在一些业余项目中积累了一点 iOS 应用编程经验,所以我在回答这个面试问题时可以稍微讲一下回调和推送等方面的内容。
我一开始讲的是我想在自己的 Instagram 版本中加入的一些功能:点赞、上传照片和简单的时间轴。我非常了解这些场景的功能,因此我能够构建一个非常可靠的 API。
然后我画了一些概要设计图片,介绍了客户端如何与后端交互,以及后端如何存储数据。
我从小处着手,然后在需要的地方添加更多的组件,并主动寻找瓶颈所在。我做了一些有根据的猜测(而非盲目的猜测),以及每一项技术是如何融入进去的。同样重要的是,也需要知道什么技术无法很好地融合进去。
例如,为什么要使用 Cassandra 而非 MySQL 来存储某些信息,为什么要使用 OAuth 而不是简单的认证,是使用 Cassandra 还是 Memcached 来缓存数据,是使用流媒体还是批处理等等。
在这里,你需要探索的领域还有很多。因此仅仅通过一个小时的沟通是不够的。为了能够更好地回答这类面试问题,你必须阅读并学会权衡和取舍。一个行业的技术优势和劣势是什么。为此,我推荐一个网站:HighScalability。
回答这类面试问题时,要做到就像和同事进行一次头脑风暴一样,做尽可能广泛和深入地探索。
你要知道,这些面试的目的是要了解你的知识面的广度和深度,这是一个让你脱颖而出的机会,这一点很重要。我在 Youtube 上看了一段关于如何解决设计问题的视频,它为我在回答设计类面试题中提供了巨大的帮助。我从中学到的两个主要经验是:推动设计对话并展示自己。
我列出了自己在下面这些领域里的能力水平:数据结构(链表、散列映射、二进制树、二进制搜索树、堆、数组)、算法(二进制搜索、哈希、动态规划、排序)和特定语言的语法和库(例如,Python的lambda、附加和索引)。
我选择了自己最不擅长的领域并开始研究它:算法。
算法从来都不是我的强项。我大学毕业已经有一段时间了,在我的日常工作中,我没有花太多时间在二进位搜索上。我对每个算法的运行原理的使用场景有一些初步了解,但我无法在10分钟内写出二分查找程序,不管是在白板上还是在面试官面前都是如此。
我从亚马逊上买了一堆精美的细马克笔,效果非常好。但面试时的马克笔通常都不好用,我通常在面试时会花2-3分钟找一支能用的笔,而这2-3分钟是你浪费不起的。另外,细马克笔允许你在一个白板上写5-8行代码。
小建议:自己准备一盒马克笔。
我花了50美元从 Costco 买了一块白板,从亚马逊买了一些相关书籍,然后开始了我的编程实践。我确保我在二分查找、递归、动态规划、BFS 和 DFS 上做了专项训练。很多的面试问题都是围绕递归和二分查找展开的。我所见过的最好的面试问题是那些有很多不同解决方案的面试问题。
在参加谷歌的面试时,我曾被问到一个与文件系统目录有关的问题,以及如何遍历这些目录(提示:递归)。我很快就解决了这个问题,然后面试官问了如何在那个目录中找出一个丢失的文件。这个问题相对更难一点,但是我还是解决了。然后我们讨论了如何重建目录,如何对它进行序列化和反序列化,我们花了大量的时间讨论文件目录在底层是如何运行的。对我来说,这是一次非常愉快的面试。
面试顶尖科技公司
可以这么说,参加这类面试是一次令人神经崩溃的经历,给人的感觉如同坐过山车。
我是根据下面这个方式来分配我的时间的:20%的时间用于简历制作,20%的时间用于调查研究,60%的时间用于面试准备。
我将自己20%的时间都用在整理自己的简历上,而我的简历至少有三年时间都没有更新过了。我仔细研究了我过去做过的所有事情,并选择了一些我从头负责到底的项目,项目的复杂性则是其次。
我之所以会这么做,主要有两个方面的原因。从头到尾负责一个项目需要纪律和领导能力,这是我想向面试官重点突出的两个能力。其次,对于那些我从头到尾负责的项目,我可以向面试官深入且广泛地描述项目的各个方面。这一点在我参加 Twitter 的面试时回答有关设计的面试问题时发挥了重要的作用,在 Twitter 的面试中,面试官不仅对我负责的项目的设计工作进行了严格的考察,而且还对背后的决策进行了考察。我会把20%的时间用于调查研究。这里说的调查研究是指对自己感兴趣的公司进行调查,并寻求内部推荐的机会。通过内部推荐的方式能够大大提高求职信的回复率。
根据我自己的实际经验,我向20多家创业公司和中等规模的公司发送了求职信,只有少数几家公司回复了。但是如果得到对方公司内部员工推荐的话,那么对方公司几乎都会在一周时间内给我回复信息。
我并不善于交际,我认识的能引荐给我感兴趣的公司的人其实并不多。为了解决这个问题,我会经常使用 LinkedIn。LinkedIn里有一个搜索功能,我经常用它来搜索1度联系人和2度联系人。所谓1度联系人,就是通过接受邀请直接建立联系的会员。你可以查看他们的个人档案和人脉信息,不受限制地向对方发送站内信,还可以在你的个人首页看到对方的动态消息。所谓2度联系人,就是已经与你的1度联系人建立联系的会员。通俗理解就是你好友的好友,一般是没有建立直接联系,但和你可能有交点的人群。免费账户可以看到2度人脉的个人档案,可以看到和对方的共同联系人,但不可以直接发站内信。
LinkedIn的搜索功能
这是非常重要的,因为给一个人你不认识的人直接打求职电话是非常困难的。当接到陌生电话时,人们通常都非常谨慎,通过这种方式很难快速建立信任关系。LinkedIn 在我调查研究阶段对我的帮助非常大。
回顾我面试过的所有公司,以下是我对每一家公司的看法:
Facebook/Google:很机械化。标准的面试流程,我和这些公司无法建立任何情感连接。
Pinterest:在这家公司的面试体验并不是最好的,但这家公司是一个很酷的公司,产品也很酷。
微软:我非常喜欢我所面试的团队,尤其是团队经理。标准的面试问题,但是非常个性化。是我的第二选择,当然这个因人而异,微软每个团队的面试风格是各不相同的。
Amazon:标准的面试流程。大概有50%的人会喜欢这种面试风格,也有大概50%不喜欢这种面试风格。
Twitter:面试流程非常有趣和个性化。我个人非常喜欢它的面试流程,非常重视个人和我过去做过的事情。
Snapchat:在洛杉矶有非常酷的办公室,有很多人都决定在创业的大潮中加入其中。
Lyft:离我住的地方不远,办公室很不错,标准的面试流程,我对这家公司没有太强烈的感觉。
面试 Twitter
从很多方面来说,我认为要通过 Twitter 的面试都是非常困难的。但与此同时,Twitter的面试流程比我面试过的其他任何公司都更有趣、也更个性化。
Twitter 的面试流程大致是这样的:与一个工程经理进行简单的电话面试。接下来是一到两轮的技术电话面试,这取决于你的表现。如果通过电话面试,他们会把安排你到应聘工作地点进行现场面试,我是在西雅图参加的现场面试。一共有3轮1小时15分钟的现场面试,每场面试都有两个面试官。
最开始的两轮技术电话面试都是标准化面试,你需要在一个共享的编码文档中通过编程来解决实际的问题。
现场面试更像是一种双方的互动交谈,也不会让人感到太害怕恐惧。面试官会问一些关于你过去参与过的项目的深度问题,他们会询问你过去做过的事情。如果你过去曾负责过一个项目,那么面试官就会问一些有关这个项目的问题。面试官鼓励你用这些项目作为参考,并从中来试探你的想法。
其它公司的面试感受
相比之下,我觉得 Facebook 和谷歌的面试更加机械化。他们有1-2轮的技术电话面试,5到6轮的现场编程考核。每一轮面试都需要你在白板上进行编码,还要要求你在一个相对合理的时间内完成一个近乎完美的解决方案。
Facebook 有两轮编程面试,一论设计面试,一轮行为面试。
谷歌有5轮编程面试,都和设计无关,期间没有一位面试官问我之前做过的项目。虽然我并不认为这是一种糟糕的面试方法,但这种面试让我感觉太机械化了,并没有给工程师提供多少机会来展示他们的能力。有些人在这种面试中表现得非常好,就像有些学生在考试中表现优异一样。
我并不是喜欢在 Pinterest 的面试体验。我认为 Pinterest 这款产品本身非常有意思,他们的工程技术团队似乎也在解决一些非常酷的技术问题。但是我在 Pinterest 的面试体验却是非常糟糕的。
Pinterest 有三轮编程面试、一轮设计面试。在这4轮面试中,设计面试是最让我失望的。为什么这么说呢?面试官迟到了,他花了几分钟时间浏览我的简历,然后开始在白板上画一些 API。他简短地描述了他期望 API 做什么,并问我该如何解决这个问题。我们阐明了 API 的特性,然后我开始使用白板描述我的解决方案,大概5分钟后,我转过头发现他竟然睡着了。这次面试体验太糟糕了。我在一项调研问卷中向招聘人员反馈了这个问题,但是没有收到任何回复。
我就不详细和大家分享我在面试中被问到的所有问题的细节了,不过我想和大家分享我在准备面试的过程中学到的一些经验和有用的技巧。
我的面试总结:
简历内容一定要做到实事求是。大多数公司的面试官会问一些关于你的简历上的内容的问题,面试官通常能够根据你的回答判断你的简历内容是否作假。此外,对一个项目做到100%的了解要比对10个不同项目分别只有10%的了解要好得多。
简历最好只用一页。对于科技公司来说尤其如此,因为科技领域有一个普遍的共识,只有当你有博士后的研究经历或者亲自深度负责过很多项目,这时你的简历有2页或更多页才是合理的,否则最好用一页。
多社交并建立自己的人脉网络。软件工程师职位的竞争非常激烈,这些顶尖的科技公司每天要筛选成千上万份简历。如果你应聘的公司内部有员工帮你内推,那么你的简历被关注的可能性会更高。
精心准备面试内容。每一个对你感兴趣的公司都想知道你为什么对他们感兴趣。一个糟糕的回答是:我现在急需找到一份工作赚钱支付账单。一个不那么糟糕的回答是:我在网上浏览,发现了你们公司,好像你们在做一款非常有趣的产品。一个很好的回答是:我知道你们公司在X领域做了一些有趣的工作来实现Y。我在过去做过一些工作,这是我学过的关于A、B、C的知识,这些知识可能与X领域有关。我对Y非常感兴趣,因为......(不要将这当作一个固定的模板。相反,你应该从中找到模式,——做充分的调查研究,向你应聘的公司展示为什么你和这家公司是非常匹配的。)
其它建议
技术面试是非常困难的。然而,最好的机会是留给那些做了充分准备的人。
早做准备,而且要做充分的准备。每个人都知道他们应该为面试做准备,但大多数人都不知道如何才能真正做好准备。就像任何值得做的事情一样,需要刻意练习才能在某件事上有出色的表现。而刻意练习意味着你需要有一套系统。
建立一套用来练习技术技能的系统。我会根据1-10分的评分方式对自己的表现进行评分,并努力提升自己最不擅长的领域。我花了好几天时间研究不同类型的面试问题,直到我完全掌握了每个概念。我每天都在 Evernote 上做笔记,笔记内容包括编程技巧、常见错误和误解、用于解决特定问题的框架等等。
我的笔记
将你掌握和学会的知识记在本子上。我同时使用 Evernote 和 OneNote 来记录和追踪事情。我用 OneNote 来记录技术方面的内容或代码,因为我可以按照自己喜欢的方式来对这些笔记进行格式化。我用 Evernote 写一些文章或感想。上面的图片显示的是我在架构和系统设计上的一些想法。
Evernote 用于记录想法
把所有的事情都记录下来,即使你认为你不会用到它也要记录下来。我非常健忘,所以我会将我学会的任何东西都记录下来,包括 shell 命令。我会时不时地阅读技术博客,如果我发现任何有趣的东西,我都会立刻在 Evernote 上将其记录下来。我会每星期或每月对记录过的内容做一次整理优化。这个习惯在我的职业生涯中对我的帮助很大。
模拟面试。这绝对是非常有价值的,我极力推荐大家这样做。我会和朋友一起进行模拟面试,并尽可能多地练习。如果你找不到朋友一起进行模拟面试联系,那么我推荐你使用 Refdash,这是一款“面试即服务”的产品。这个平台上有一群在谷歌、Facebook和微软等大型科技公司工作的面试官。这些面试官会评估你的编码和设计技能。最重要的是,在每次模拟面试后它都会给你打分,并给出一些具体可行的改进方法。
容忍自己的失败。在我整个应聘过程中,我经历过很多次的失败。有时失败只是因为你运气不好。即使你面试失败了,这对你来说也不是世界末日。公司在招聘的过程中倾向于说“不”,因为这对他们来说风险更低。从长远来看,犯假阳性的错误比假阴性的错误的成本更高。最初的几次拒绝给人造成的打击最大。当我刚开始面试的时候,我几次电话面试都没有通过,我的自信心也受到了严重打击。我对自己的能力也开始心存怀疑,并开始担心自己的技能在当今的就业市场中已经不受待见了。然而,我给自己支了一招:如果你失败了10次,那么再多尝试10次。你所需要的只是一次成功,这种安慰给了我很大的信心,让我能够不断尝试,当我拿到第一个 Offer 之后,后来的其它 Offer 来得就会容易很多。
我花了大约两个月的时间来为我的面试做准备并做各种模拟练习。我每周大概会在这方面花20个小时,或者每个月花80小时,在全职工作之余进行学习和记笔记。
为了充实我的简历,我花了3年半的时间努力工作。在日常工作中,我会有意识地选择那些困难且棘手的任务,这样我就能比其他人学到更多东西。尽管我并非毕业于常青藤名校,之前也没有在顶尖科技公司工作的经验,但我对我所负责过的项目有一个清晰透彻的理解,并在简历中体现出这一点,从而让自己在面试中能脱颖而出。这是有可能做到的,因为我做了很多研究,并将我学到的所有东西都记录了下来,并建立一个用来练习技术技能的系统。
要记住:坚强的人能够生存,坚韧的人能够茁壮成长。
小结:不要放弃,为机会而时刻准备着,多练习,并始终充满希望。专注于过程,并在整个过程中对自己严格要求。
资料推荐
书籍《Elements of Programming Interviews: The Insiders' Guide》:对解决那些非常难的编程问题非常有帮助。
书籍《Cracking the Coding Interview: 189 Programming Questions and Solutions》:涵盖了大部分的计算机基础知识。
OneNote:我使用这款工具来存储代码片段。
Evernote:我使用这款工具来记录并存储代码之外的东西。
CodeRunner:我非常喜欢这款 Mac 应用,我曾多次使用它来运行特定的 Python 脚本和函数,而且效果非常好。
Jobscan:它提供很酷的简历筛选工具。
Refdash:由一群前谷歌员工运营的产品。用这款产品来模拟面试的效果非常赞。我在 Refdash 上碰到的面试官曾在谷歌工作过,他为我指出了很多我应该关注的地方,以及谷歌面试的主要评分依据。我强烈建议你尝试一下。
CodePath:一个帮助人们进入科技行业工作做准备的非盈利组织。公司的两位负责人 Tim 和 Nathan 都是很棒的人,我从他们那里学到了很多。这个社区非常有帮助,每个人都愿意伸出援手!
Fine-point markers:极力推荐!
在我推荐的两本书中,我更喜欢 Cracking the Coding Interview(CTCI),它介绍了很多基础知识,例如链表是如何工作的,哈希映射如何工作以及如何解决一些基本问题。
Elements of Programming Interviews (EPI)非常适合解决较难编码的问题。我的使用方式是,首先花2-3周的时间大致浏览这两本书,达到一个基本的了解。
接下来集中精力阅读 EPI,因为我会开始在那里做更多有趣并且困难的事情,同时充分理解 CTCI 中的基本数据结构,以帮助我更容易地解决这些问题。
来源:CSDN(言则整编)
译者:安翔
原文:https://medium.freecodecamp.org/how-i-landed-offers-from-microsoft-amazon-and-twitter-without-an-ivy-league-degree-d62cfe286eb8
程序员大咖整理发布,转载请联系作者获得授权