当前位置:  编程技术>移动开发
本页文章导读:
    ▪【USB】USB 要害概念简介        【USB】USB 关键概念简介一,USB接口优点         简单、速度快、支持即插即用和热插拔 二,USB通信         USB通信中居于核心地位的是主机(Host),常见的USB主机是PC机。任何一次USB的.........
    ▪ 诸位大神,真心求解答        各位大神,真心求解答!为啥下面的这个小Demo会报空指针异常。。 先看布局文件main.xml <?xml version="1.0" encoding="utf-8"?> <LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:o.........
    ▪ Google, FaceBook, Amazon 加州谋职记       Google, FaceBook, Amazon 加州求职记战绩概览:Google的面试机会是师兄推荐得到的。事后来看当时完全没有准备好,实在是浪费了一次大好机会,对不住师兄。被推荐后不久,Google北京的HR联系我.........

[1]【USB】USB 要害概念简介
    来源: 互联网  发布时间: 2014-02-18
【USB】USB 关键概念简介

一,USB接口优点

        简单、速度快、支持即插即用和热插拔

二,USB通信

        USB通信中居于核心地位的是主机(Host),常见的USB主机是PC机。任何一次USB的数据传输都必须由主机发起和控制;所有的USB外设都只能和主机建立连接;任何二个外设之间或是二个主机之间都无法直接通信。所以,USB主机和USB设备的功能是不同的。  

        USB主机的功能有:

                    (1)通过USB接口给外设提供电源

                    (2)检测和配置设备(即设备的枚举)。如:它必须检测出设备的连接和拔除,了解设备的功能,给设备分配地址

                    (3)错误检查和管理数据的传输。这些由USB接口硬件保证,不必编程处理。

                    (4)根据设定的传输方式与外设交换数据。  

        USB设备的功能有:

                    (1)管理电源。设备可以由USB接口获取电源,也可能有自己的电源。设备在USB接口无通信作用超过3ms后应进入低耗电的暂停状态。

                    (2)检测通信。每一个设备都要检测通信信息包中的地址是否和本设备的地址相符,如果不符,设备就会忽略本次通信,这由USB接口硬件自动进行处理。在设备一开始连上USB接口时,使用固定的默认地址0,然后USB主机在检测阶段会给设备分配一个地址,以后的通信都按这个地址进行。

                    (3)通信数据的错误检查。由USB接口硬件保证,不必编程处理。

                    (4)响应请求。主机检测到设备连接上后,会按USB协议发送相应的设备请求来了解设备的类型和能力,并对设备进行一些配置(如设定地址和配置描述符),设备应能响应这些请求,并返回相应的应答数据。

                    (5)根据设定的传输方式与主机交换数据。


三,USB主机和USB设备之间数据的传输方式   目前,USB协议规定了四种数据传输方式:

                    (1)控制传输。主要用于主机对设备的检测和配置。

                    (2)中断传输。用来支持那些偶然需要数据通信,但服务时间受限制的设备。中断传输常常用在键盘、鼠标和游戏杆等设备上。

                    (3)批量传输。适合使用在时间不重要的场合。批量传输可以传输大量的数据而不会阻塞总线,因为它会让其他类型的传输先执行,以等待可以传输的时间,如用于磁盘操作。

                    (4)同步传输。适合用于以固定速率进行的传输,而且可以容忍偶尔的错误,如实时语音传输。


四, 设备的端点  

          任何的数据传输都是传递到一个USB设备(确切地说是USB接口器件)的端点(Endpoint),或是由一个USB设备的端点发出。

          可以把端点简单地理解成USB接口器件中的一个缓存器,用来作为数据的缓冲区,它由相应的控制寄存器和状态寄存器来管理。

          储存设备端点中储存的可能是接收到的数据,也可能是等待要送出的数据。主机也有接收与传送数据的缓冲区,不过主机并没有把它定义成端点,而是当作与设备端点通信的出发点(Starting Point)。一个USB设备可能有好几个端点,每个端点可以设置成输出或输入方向以及控制、中断、批量或同步传输方式中的一种。因为主机一开始是通过端点0来检测和配置设备的,所以每个设备都必须有一个端点0,而且其传输方式必须是控制传输(一般USB接口器件默认支持)。除此之外,设备很少需要其他的控制端点。USB协议定义了11个标准请求命令,用于在端点0以控制传输方式来检测和配置设备。


五,设备的描述符

         USB主机是通过请求USB设备的一系列描述符来获取设备的信息的。描述符是一种定义好的数据结构,其中可能包含整个设备的信息,或是设备中的一个组件的信息。主机请求描述符,设备回复描述符。目前,USB协议定义了三种类型的描述符:

           (1)标准类型。用于提供设备的基本信息。标准类型的描述符主要有:设备描述符、配置描述符、接口描述符、端点描述符以及字符串描述符等。

           (2)设备类别特定描述符。用于提供设备更详细的信息。如HID类(人机接口类)设备的类别特定描述符中的HID描述符和报表描述符,就可以用来描述设备究竟是一个鼠标还是一个键盘。如果是鼠标,则报表描述符的数据就是鼠标的按键和位移。

           (3)厂商特定描述符。也是用于提供设备的一些更详细信息,不过它是由厂商自己定义的,不像设备类别特定描述符那样是USB规范定义的。


六,数据信息包的格式

        信息包(Packet)是USB传输数据组织的基本形式,其具体意义和实际内容通过相应的一系列字段来表示,有的字段在USB协议中有定义好的关键字。

        信息包的字段类型有:   

                 (1)SYNC字段,用于信息包的开始与同步,它由硬件自动处理。   

                 (2)PID字段,信息包标识符(Packet Identifier,PID),信息包共有四种类型:令牌、数据、联络和特殊,四种类型共对应16个PID码。   

                 (3)地址字段,用于指明USB主机究竟是要和哪个设备通信,设备的地址初始默认为0,主机会在设备检测阶段给设备分配一个地址。   

                 (4)端点字段,用于指明USB主机究竟是要和设备的哪个端点进行通信。如前所述,一个设备可以有多个端点。   

                 (5)帧号码字段,USB主机把USB总线上的实际数据传输按时间分割成一块块的帧(Frame)或微帧(Micro Frame)。对于全速和低速的设备,主机将传输分成1毫秒的帧,对于高速设备主机将传输分成125微秒的微帧。帧号码字段就是用于识别特定的帧或微帧,它由硬件自动处理。   

                 (6)数据字段,为实际要传输的数据。   

                 (7)校验字段,用于信息包的数据校验,它由硬件自动处理。  


        令牌信息包有四种类型:   

                 (1)OUT,表示主机输出数据到设备;    

                 (2)IN,表示主机从设备读取数据;    

                 (3)SOF,表示帧标号开始;  

                 (4)SETUP,专门用于控制传输的设置事务。

        

七,事务

       USB协议规范将事务定义为“将一个服务传送到一个端点”,这里的服务指的是主机传送信息给设备,或是主机从设备接收信息。每一个传输可以包含一笔或多笔事务,而每一笔事务可以包含一个、二个或三个信息包,可以把信息包理解为数据传输物理上的基本单位。

       大部分事务都包含三个信息包:令牌信息包、数据信息包和联络信息包。根据令牌信息包的PID标识,事务一般分为三种类型:输入(IN)事务、输出(OUT)事务和设置(SETUP)事务。

       每一种传输类型(控制、中断、批量以及同步)包含一个或多个阶段,而每一个阶段包含一个或多个事务。具体说来,在控制传输中,一般包含设置事务阶段(对应于设置事务类型)、数据阶段(对应于输入或输出事务类型)以及状态阶段(对应于输入或输出事务类型),而中断、批量以及同步传输中只包含数据阶段。

      (1)设置阶段包含一个设置事务(由令牌信息包、数据信息包和联络信息包组成);

      (2)数据阶段可能由多个事务组成,一般每个事务也是由令牌信息包、数据信息包和联络信息包组成的(只有同步传输的数据阶段的事务中不包含联络信息包);

      (3)状态阶段包含一个事务,该事务也是由令牌信息包、数据信息包和联络信息包组成,不过数据信息包的内容为空,状态阶段只用于控制传输,以表明整个控制传输是否成功。

      USB设备驱动程序的设备驱动程序的加载在主机从设备描述符了解到设备的信息后,它会寻找一个最合适的驱动程序来管理主机和设备的通信。在选择驱动程序时,Windows会试图将系统的.inf文件内的信息与从设备内读出的厂商和产品ID以及版本号作比较,如果相符,就根据相应的.inf文件加载驱动程序。如果Windows找不到合适的.inf文件,它会显示一个“添加新硬件向导”来让用户指定驱动程序。 


八,USB设备的设计    

        USB规范定义了许多设备类型,用不同的设备类别码和接口类别码来表示,如:

             (1)HID(Human Interface Device,人机接口类设备)设备类别码是0x00,接口类别码是0x03,HID类的设备有键盘、鼠标以及游戏杆等;

             (2)Mass Storage(大容量存储设备)的设备类别码也是0x00,而接口类别码是0x09,Mass Storage类的设备有软盘、硬盘、光盘以及FLASH盘等;其他还有显示器类、通信设备类、音频设备类等。USB规范中还有一个特别的Vendor Specific类设备,用于厂商自定义设备类型,其接口类别码为0xFF。所以,设计者总是可以找到一种适合自己要设计的设备类型。  

        设计USB设备时,首先要确定好设备到底属于哪个类别,然后要实现基本USB通信协议以及设备的类别通信协议。例如,U盘属于Mass Storage设备,所以设计U盘时,除了要实现基本的USB通信协议,还要实现大容量存储设备类规范中的UFI命令规范。由于Windows 提供了对Mass Storage 协议的支持,因此U盘只需要遵循Mass Storage 协议来组织数据和处理命令,即可实现与PC 机交换数据。一般来说,一个USB设备的完整设计过程主要包括四个部分:    

              (1)USB硬件接口的设计;    

              (2)设备固件的编程;   

              (3)PC端设备驱动程序的开发; 

              (4)PC端设备应用程序的开发。 

九,USB硬件接口设计

        USB接口芯片一般有二种选择方案:

              (1)USB芯片本身就是一个微控制器,如Cypress的EZ-USB系列芯片,与8051兼容,大部分EZ-USB芯片支持最大数目的端点(一个控制端点0以及30个额外的端点)以及所有的4种传输方式;

              (2)USB芯片只处理USB通信,所以它必须由外部的微控制器来控制,如PLILIPS的PDIUSBD12,它符合USB1.1规范,包含默认端点0在内共有3个双向端点。 

十,控制器的固件编程

        USB接口芯片收到数据或发送出数据后都会产生中断,所以固件编程的核心就是编写中断服务程序。这项工作主要就是根据相关寄存器的标志来对各个端点缓冲区的数据进行处理。可以把中断服务程序分为一些功能模块(函数)来考虑:

          (1)端点0的响应。当设备插上USB接口后,主机会发出一系列的请求给设备的端点0,设备的固件程序应该能在端点0对这些要求进行正确响应。

          (2)其他端点的数据通信过程。通过(1)主机就能知道设备端点的使用情况,以后就可以通过其他端点以设定的传输方式来交换数据。

          (3)实现设备类别遵循的协议规范。例如,如果要设计U盘,则U盘的固件程序就要实现对Mass Storage Class规范中的UFI命令规范的支持。 

 十一,PC端驱动程序的开发

            在Windows内执行的USB设备驱动程序,必须符合Microsoft定义的Win32驱动程序模型(Win32 Driver Model,WDM)。它是一种分层的驱动程序模型。Microsoft提供了Windows DDK(Windows Device Developer′s Kit)工具和VC编译器来编写WDM驱动程序,具体请参考相关的开发指南。也有许多第三方的工具软件可以用来编写USB的WDM驱动程序,如Jungo 的WinDriver USB。使用这类工具软件不需要深入了解WDM的编程细节。

PC端应用程序的设计端

        在Win32系统中,操作系统把每一个设备都抽象为文件,应用程序的设计只需要通过几条简单的文件操作API函数,就可以实现与设备的驱动程序通信。这类  Win32函数有以下几种: 

                    (1)CreatFile函数,用于打开一个设备,返回一个与设备相关的句柄;

                    (2)ReadFile函数,用于从设备中读取数据;

                    (3)WriteFile函数,用于向设备写数据;

                    (4)DeviceIoControl函数,用于对设备进行一些控制操作,如更改设置等;

                    (5)CloseHandle函数,关闭一个由CreatFile函数所打开的设备,函数的参数为CreatFile函数返回的设备句柄。还有其他一些和USB设备类别相关的API,可用于获取设备的信息,如设备路径和名称等,具体请参考相关的开发指南。


    
[2] 诸位大神,真心求解答
    来源: 互联网  发布时间: 2014-02-18
各位大神,真心求解答!

为啥下面的这个小Demo会报空指针异常。。

先看布局文件main.xml

<?xml version="1.0" encoding="utf-8"?>
<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
    android:orientation="vertical"
    android:layout_width="fill_parent"
    android:layout_height="fill_parent"
    >
<TextView  
    android:layout_width="fill_parent" 
    android:layout_height="wrap_content" 
    android:text="@string/hello"
    />
 
<ListView 
    android:id="@+id/listview1"
    android:layout_width="fill_parent"
    android:layout_height="wrap_content"
></ListView>

</LinearLayout>

再看Activity文件

public class AndroidListViewActivity extends Activity {
	private ListView listView ;
    /** Called when the activity is first created. */
    @Override
    public void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        
        listView = (ListView)findViewById(R.id.listview1);
        
        listView.setAdapter(new ArrayAdapter<String>(AndroidListViewActivity.this,android.R.layout.simple_list_item_1,
        		new String[]{"测试数据1","测试数据2","测试数据3","测试数据4","测试数据5","测试数据6","测试数据7"}));
        setContentView(R.layout.main);
    }
}



为啥要报空指向异常呢?这个Adapter哪里有问题呢?各位大神指点迷津啊!

3楼u010124782昨天 19:58把private ListView listView;提到Activity外面,然后把setContentView(R.layout.main);提上到super.onCreate(savedInstanceState);下面一行2楼lszsalleter昨天 16:30未调用setContentView(R.layout.xxx)Re: Main_Stage昨天 17:18回复lszsalletern谢谢赐教! 非常感谢。Re: Main_Stage昨天 19:58回复lszsalletern不是啊,setContentView(R.layout.main)也是错的,还是会报错。是Adapter的问题。但是不晓得哪里出错了。1楼yanjiangbo06昨天 11:43setContentView(R.layout.main);放到super.onCreate(savedInstanceState);下面。你界面都没onCreat就直接指定adapter,肯定会报空指针了。Re: Main_Stage昨天 14:06回复yanjiangbo06n谢谢赐教! 这个问题,我懂了! 非常感谢

    
[3] Google, FaceBook, Amazon 加州谋职记
    来源: 互联网  发布时间: 2014-02-18
Google, FaceBook, Amazon 加州求职记

一年多前,出于显而易见的原因,下定决心肉身翻墙。经过一番考虑,放弃了读书这条途径,决定直接找工作,通过H1B签证出去。于是去年八月份从百度辞职,开始着手准备。当时觉得今年拿到H1B的成功率大致能有个六七成,加上周围朋友们的不断鼓励,可以说还是相当自信的。然而,时至今日,在历经Google、Amazon、Facebook三家公司之后,这第一次尝试却可耻地失败了……


战绩概览:

  • Google:仓促应战,HR电面一轮,技术电面一轮,北京onsite两轮,惨败;
  • Amazon:技术电面两轮,在面试官反馈良好的情况下莫名挂掉,详情见下;
  • Facebook:HR电面一轮,技术电面两轮,Menlo Park总部onsite五轮,惜败;
  • AeroFS:因为是startup,临时告知无法提供H1B,于是告终。

个人背景参见这里(原作者,本文系转载)


失败的原因,简而言之就是两个字——自大。在百度四年多,技术方面长进不少;虽然从未以做管理为目标,却也阴差阳错地干了两年管理,从零带出了一支二十多人的研发队伍,同样获益颇丰。再加上离职时恰逢耗时一年之久的首部译作正式出版,自我感觉良好,信心爆棚。周围的朋友和同事们听说了我的计划之后都鼓励说“肯定可以”,于是我也就飘飘然地认为“肯定可以”了。这种自大心理使得我没有尽早将目标公司的面试方式研究透彻,也未能及时采取最为有效的方法弥补自己客观能力上的不足。

无论如何,这段经历还是相当宝贵的:经历了第一次英语面试、第一次办签证、第一次出国、第一次倒时差,还有第一次误机…… 虽然求职失败,但仍然获益良多。本文便是对这次求职全过程的记录,一方面警醒自己,一方面也为其他有类似打算的朋友们留一个参考。由于几家公司的面试是交错进行的,下文并没有完全按照时间顺序进行描述。此外,出于NDA协定等原因,本文不会透露具体的面试题。


面试准备

虽说去年八月份就已经正式离职,但实际上前几个月都忙于其他事务,做了一些之前一直想做但是没有时间做的业余项目。期间虽然也不断补习各种基础知识,但一直不得要领,进度甚缓,效果堪忧。于是一直觉得没有准备好,迟迟不敢真枪实弹地进行面试。真正进入状态应该是十二月份以后了。面试准备当然少不了看面经,其中最有指导意义的几篇分别是前同事Cat Chen的Google、Microsoft、Yahoo、Facebook系列面经和博客园上的这篇拿了9个offer的传奇面经。其中,后者给出的各种参考材料尤为有价值,我自己后期真正有效的面试准备基本上也是跟着这篇面经的框架来的。


算法基础

众所周知,湾区的公司在面试时非常注重实际编码能力,要求直接在线或在纸上、白板上写代码,并且要求是可编译的零bug代码,因此有ACM背景的应聘者会非常占优。当然,不同公司在严格程度上也不尽相同,比如Amazon对无伤大雅的手误或API细节记不清等情况相对宽容,Facebook次之,Google最严格。反观国内的互联网公司,虽然面试时也会问算法问题(尤其是对应届生),但一般不太会要求手写达到可编译运行质量的代码(要求写伪码的居多);同时考量的知识面也会更广、更开放一些。一开始我觉得湾区的这种面试方法并不科学——毕竟实际工作中没人会要求你在不借助调试器等工具的情况下一次性编码成功。而且,竞赛类算法题的代码和工业界的代码完全就是两种套路(在工业界干过几年的前ACM选手们应该非常清楚)。但反过来一想,自己周围能够达到这个水准的,无一不是牛人。而且这个方法高度统一,易于判定,在大规模面试中更利于统一面试官的评判标准,从而达到严格把关面试质量的目的。总而言之,这种面试手段跟高考有点类似——它可能不是最为合理的选拔手段,但对于大公司来说,为了保证更大范围内的公平性和质量,似乎也没有更为合理的手段,因此就现阶段而言它也就是最为合理的手段了。

就我个人而言,在校时顶多也就参加过ACM校赛;无论刷题速度还是数学和算法基础都远逊于专业选手,纯粹是玩儿票水准。工作六年多更是基本告别基础算法,顶多也就是算个时空复杂度,偶尔用一次微积分都会感慨万千原来这玩意儿还真有用得上的时候。再者就是平时写程序的习惯。经过严格训练的ACM选手可以做到解题时从头至尾一气呵成,当年ZJU校队神人们直接在提交框里写码提交一次AC的传说屡见不鲜。我平时自知是个粗心鬼,写程序一定是先搭架子后填肉,边填边调;要是妄图一次成功,那最后多半是错得没边儿。所以,算法基本功以及编码不够快、准、狠,就是我最大的弱项。

为了弥补这些不足,我最早采用的方式是啃Algorithms、The Algorithm Design Manual等大部头。然而实践证明这个方法收效甚微。当然不是书不好,而是心态问题。这些大部头行文严谨,事无巨细悉数记录在案,最适合用作教材或是当作手册日常翻阅。对于目标主要是查漏补缺的我来说,从头到尾看一遍太慢,而且一不小心就陷入细节或是一些事后证明完全没有必要钻的难点;跳着看又不知道到底哪里是自己缺漏之处,无的放矢。

要想搞清楚缺漏之处究竟在哪,最有效的办法还是实际做题。做不出来的自然就是缺漏,重点补习;做得出来的则尽量争取一次到位,追求编程速度。在这条路上先后尝试了CareerCup、ZOJ、TopCoder和LeetCode。四个站点的优缺点对比如下:

  • CareerCup

    作为全世界码农应聘者交流面试经验和真题的集散地,其优点自然就是真题丰富。缺点也很明显:很多题目描述不严谨,边界情况模糊;没有OJ,自己的代码正确与否难以得到客观准确的判断;参考答案仅限于用户贴出的代码和思考,而且CareerCup论坛的代码排版效果恶心得令人难以置信,你几乎不可能贴出一份缩进正确的代码!

  • ZOJ、TopCoder

    ZOJ实在是太熟悉了,本科时闲来无事就在ZOJ上切题。TopCoder交互比较复杂,但流程基本上差不多。二者都是OJ,因此自己的代码正确与否、效率如何,都可以迅速判定。TopCoder相对于ZOJ的一个优点是可以检索指定难度和类别的题目。缺点则是这二者都是竞技平台,当OJ判定代码错误时不会输出额外的诊断信息,一旦陷入难以想到的边界情况就会花费大量时间。

    此外,就这次的经验来看,ZOJ的题和TopCoder 500分以上的题在平均难度上比实际的面试题要高不少。与其在难题上耗费过多时间,多切一些简单题提高写代码的熟练程度可能更有帮助。

  • LeetCode

    LeetCode可以说是结合了CareerCup和ZOJ、TopCoder的优点:既有真题,又有OJ。而且当OJ判定代码错误时,会同时输出对应的测试用例,大大方便了调试。在面试准备的后期,我完全转向了LeetCode,训练效果显著。对了,目前LeetCode后台的C++编译器已升级到g++ 4.7.2,支持大部分C++11特性(尚不支持lambda),写起C++来舒心不少 :-) 就这次的经验来看,实际面试题的难度跟LeetCode的平均难度相差无几。缺点则是题量较少,目前仅有100多题,覆盖面较窄(例如二叉树的题有一大堆,而图论题则几乎没有)。

这里引用Cat在他的Facebook面经中说的一段话:

 让我「大开眼界」的是面试题,原来真正好的面试题并不在于它有多难,而在于它有多简单,简单到熟悉这个领域的人一下子就明白到你在说什么以及想问什么。能够进入 Facebook 的人应该都觉得面试不难,至少跟中国的面试对比起来如此,那是因为 Facebook 把觉得面试有点难的人都过滤掉了,而中国那些很难的面试反而没什么区分度。

就我自己的经历来看,的确如此。从难度上说,至少在电面阶段,Google、Amazon、Facebook的算法类面试题都是入门级的题目。给我的感觉有点像是考研——题不在难,而在区分度,考的是基础是否足够扎实。题目拿到手会做的话立马就能下手,即便不会做也会觉得这道题很眼熟。Facebook onsite面试题的难度基本上也在这个水准。Google和Amazon两家都没有进行到最后阶段,不知道后续的难度是否会有提升。从别的面经上来看,Google的算法题在难度上要更胜一筹,Amazon则会有一些面向对象类的系统设计题。


英语沟通

虽然对自己的英语还算有信心,但此次面试前基本上没有跟老外面对面沟通过,所以第一次英语电话面试的时候紧张得语无伦次,经常听不清面试官在说啥,好在从第二次开始就完全无压力了,窍门很简单:提前打招呼让面试官说慢点……说的时候不需要担心语法错误之类,正如某篇面经所说,人脑的纠错能力还是很强悍的,就算一个词一个词往外蹦,老外一般也能够理解。

跑题说一说口语练习,这方面好像没法短期突击,只能靠平时多磨刀。英语口语,一是口音,二是流利程度。口音的问题,我是中学的时候靠听英语歌并极力模仿歌手的发音解决的。至于流利程度,自然是靠多说。但周围没有说英语的人咋办呢?我的办法比较偏门——自言自语。以前在学校和公司里的时候,出于种种原因经常需要做技术分享,必须确切明白地把事物讲清楚。久而久之逐渐发现判断自己有没有把一个概念搞明白,最直接的办法就是看能不能把这个概念跟新手讲清楚,于是日常学习的时候也经常在脑袋里做模拟。就这样,渐渐染上了自言自语的毛病,即面对假想的听众把自己的思路讲出来,一边讲一边揣摩听众可能的反应并反复调整说辞,直至表述准确易懂为止。再加上近年来看的文献基本上都是英语,很多术语根本找不到合适的中文翻译,脑子里两个locale切来切去太麻烦,渐渐就养成了用英语自言自语的习惯,无意间变相练习了口语。当然了,这种手段只能锻炼到专业技术方面的内容,日常沟通是覆盖不到的。不过对于面试来说,刚好够用。


面试过程

1) Google

Google的面试机会是师兄推荐得到的。事后来看当时完全没有准备好,实在是浪费了一次大好机会,对不住师兄。被推荐后不久,Google北京的HR联系我。电话聊了大概半个多钟头,了解了一些背景情况,然后便着手帮我安排电话面试和onsite面试。

电话面试的面试官是美国的华人工程师,全程说的是中文。由于时差,面试时间是北京时间早上八点(对方的下午四点)。简单问了一些之前的工作背景就开始做题,大致是写一个类,模拟TCP栈的收包逻辑。写完之后又要求改为多线程版本,类似于一个生产者消费者模型。Google电话面试时是在Google Docs上在线写代码的。头一回写,动作比较慢,总体上超时比较多,而且第一次给出的解法虽然没有错但并不高效。多线程版本快写完的时候SSH隧道竟然断了(Google Docs直接访问不稳定,保险起见是翻墙访问的)!由于面试已经超过预订时间,面试官就说算了,面试结束后发到他邮箱好了。最后是例行的问答时间,不记得当时自己问的是什么问题了。

虽然面试官让我把最后一个问题的代码用邮件发过去,他却没有给我留邮箱,事后是通过HR转发给面试官的。此外面试结束后发现面试官给出的多线程的条件有误,会导致系统死锁。于是写了封长邮件,解释了会导致死锁的时序,给出了两种可能的,并附上了详尽的测试用例,顺便优化了一开始效率不够高的数据结构。当然,过程中没有查阅其他资料,完全是独立思考的。

约莫一周之后,HR帮忙敲定了位于五道口的onsite面试。两轮面试各45分钟,都是算法题,要求在纸上写代码,面试后纸张由面试官回收,似乎是要誊写到面试反馈中去。第一轮的题目很经典,简单到现在根本不好意思说自己曾经做不出来……如果是一个月后的我的话,毫无疑问可以秒杀,但当时却严重卡壳。第二轮的题目稍有一些纵深,DFS搜索加字典树加接口设计,也不是很难;面试官持续要求优化,最后一个优化点我在最后一分钟才想出来。面试末尾仍然是例行的问答环节,由于之前做了几年即时通讯,我便问了一下Google在实时互联网应用方面有没有什么规划,但由于面试官不是这一领域,无法给出什么实质性的内容,相互嗟叹了一下Google Wave之后面试结束。

两轮onsite下来,自我感觉非常不好,事实上这也是我这段面试经历中表现最差的两轮——没有一道题能够在规定时间内给出完整、无错的代码。回想起来,这个结果跟我当时的复习策略有很大关系:当时我还处在看算法大部头,辅以ZOJ/TopCoder做题的阶段,基本上是什么题难做什么题,后果就是每道题都钻很久,解题时间很长,完全没有达到训练编程熟练程度的目的。再加上纸上写代码一涂改就乱七八糟一团,越写越紧张……就面试中写代码的方式来说,我觉得用CollabEdit或Google Docs在线编程最轻松,因为跟平时写程序差不多(当然如果是平时被VS/VA、Eclipse宠坏了那就两说了);白板上写代码次之,因为写错的、不满意的地方可以随时擦掉,保持整体整洁;纸上写代码最难,一不小心就涂涂改改搞得一团乱麻,既影响自己的情绪也影响面试评价。

虽然Google的面试只进行到第二轮onsite,但可以看出Google的面试要求还是比较高的。面试官在关注代码的正确性的同时,也会关注编程风格甚至接口的注释。此外,Google的HR工作做得很到位,面试前给我发了详尽的准备材料,邮件回复也很及时。最后电话通知面试结果的时候HR先是问了我自己的感觉,然后结合面试官的评价委婉地给出了结论。


2) Amazon

Amazon的面试机会是同学推荐得到的。和HR全程邮件联系,反馈速度极慢,一个来回至少一周。和我联络的HR的工作时间跟Amazon总部差了几个小时,不知道是不是外包。

Amazon的第一轮电面是我第一次跟老外电话沟通,起先觉得没啥,但临到面试时却紧张得一塌糊涂——面试官语速太快,听不明白啊……由于沟通不是很顺畅,之前的工作背景介绍得比较失败(之前有准备过,但是一紧张全忘了)。面试官的态度虽然很nice,但听语气似乎比较失望。之后,面试官对我申请的AWS组做了一个简要介绍,然后便用CollabEdit在线做了两道字符串的题,过程还算顺利。面试完毕之后review自己的代码,发现有两处小错误,再加上一开始沟通不顺,沮丧地想应该是没戏了。

没想到过了大概两周多,在接到Facebook的onsite面试通知之后,Amazon的HR发邮件过来说打算再进行一轮电话面试,向我征询可用时间。回复之后又过了大约一周,才总算敲定了面试时间。

这个时候我已经有了Facebook三轮电话面试的经验,LeetCode也切了不少题,纸上写代码虽然还欠,但在CollabEdit这样的在线编辑器上几分钟切一道简单题对付电话面试已经完全没有问题(早点知道LeetCode就好了)。于是第二轮电面异常顺利。一上来面试官问我选数据结构的题还是算法的题,我选了数据结构题,半小时多一点切完两道。做第二道题时我把一个条件理解错了,面试官指出后像我道歉说是自己描述不够清楚,好在算法整体上差异不大。做第三道时,面试官鼓励说能做到第三题的候选人不多,因为时间所剩无几,就不要求写代码了,给出思路即可。第三题讨论完毕还剩几分钟,愉快地进入问答环节。末了,面试官给了很正面的评价,大致是说不太会有负面反馈,HR后续应该会安排到Seattle的onsite面试,当然他并没有把话说死。

然而,接下来的情节发展就比较坑爹了。

Amazon第二轮电面结束之时,去Menlo Park参加Facebook onsite面试用的B1签证已经搞定,但具体行程还未确定。本想如果Amazon的HR能够及时跟进后续安排的话,就一次搞定两家的onsite。然而Amazon的HR迟迟不见回复。由于是第一次出国,担心忙中出错,便决定Facebook面试完毕后立即回国,大不了Amazon的安排下来之后再跑一趟。于是跟Facebook安排的旅行社沟通,将行程定为面试后第二天回国。又过了大约一周,Amazon的HR来信说对不起,经过比较我们选择了其他的候选人云云,具体原因则完全没有提及。这么莫名其妙地挂掉实在是令人恼火,但当时对Facebook抱的期望还比较大,并没有太在意,心不在焉地回了封thank you了事。现在想来应该进一步追问一下被拒的原因的。总之,Amazon的面试官给我的感觉很好,但HR的跟进速度和质量实在无法让人满意。


3) Facebook

Facebook的面试机会同样是同学推荐获得的,这也是这次求职经历中走得最远的一次。正如Cat在他的面经中所述,Facebook的HR邮件回复非常及时,而且经常在非工作时间回复,整个过程中非常认真负责,不得不赞一下。Facebook的第一轮电话面试是由HR进行的,时间是Amazon第一轮电话面试的第二天早上,而Amazon第二轮电话面试那天,Facebook方面已经进行到委托旅行社替我安排onsite行程的阶段了,其工作效率可见一斑。

HR电话面试

之前从Cat的面经中看到Facebook会在HR面的时候问一些基础的问题,并留一道作业题。但我的HR面试却只问了过去的工作背景。后来了解到Cat所说的情况是前端工程师招聘流程特有的,而我申请的是Infrastructure组,就没有这一环节了。如前所述,Facebook HR面的前一天就是Amazon的第一次电话面试,有了前一天沟通不畅的教训,面试前我将想得到的问题和之前的工作背景等信息全部写了下来,实践证明非常有效。对方了解到我有管理经验但仍然希望做一线工程师之后似乎很满意(这确实是我的真实意愿)。末了约定了下一次电话面试的时间。这次面试进行了大约半个小时,就沟通顺畅程度而言比Amazon的第一次电话面试要好多了。

技术电话面试

接下来的电话面试是技术面,面试官是位女性,看名字觉得是中国人,事后果然在LinkedIn上查到是毕业于交大的同龄人,仰慕。虽然面试官是中国人,但仍然是用英语交流的,因为语言沟通能力本身也是考察环节之一。此外,由于这是该面试官的初次面试,还有一人旁听。一上来仍然是简单介绍下背景,介绍期间面试官通过邮件将CollabEdit上面试用的白板地址发送给我。点开之后CollabEdit戏剧性地报出500 Server Internal Error。然后面试官似乎比我还要手足无措,经旁听的工程师指点后转战Stypi继续面试。第一题要求解释下大端序、小端序,并写个函数判断本地字节序,秒杀。然后是一道二叉树相关的题,写了一个递归版本,途中犯了一个小错误,经提示后纠正;通过后面试官要求再写一个迭代版本,写了一半有点卡壳,面试官提醒了两次我都没能走上正轨,直至面试时间结束。

面完之后比较郁闷,因为那道题并不难。结果如厕时猛然意识到之前错在哪里——马桶和浴缸果然是灵感迸发的绝佳场所……由于面试过程中面试官曾给我发过一封邮件,我就迅速回复了一封邮件,给出了一份带有测试用例的可编译的代码。之后面试官很礼貌地回信说这是她第一次面试,我在面试时给出的解法和她熟悉的套路不一样,因此不知道该如何提示和引导,同时表明已在面试反馈中建议再找一名更为资深的工程师对我进行面试,“可能”还会有一次机会,并祝我好运。

之后便是焦急地等待。求职过程进行到这个时候,Google方面已经被拒,Amazon的第一次电话面试让我很沮丧,Facebook的这次面试前景似乎也很黯淡。等了好几天没有回音,一度令我很是消沉,每天只是默默地在LeetCode上切题。不想临近春节,Facebook的HR发来邮件预约第二次技术电话面试,没多久Amazon的HR也发来面试预约邮件,师弟@mikeandmore2又通过邮件帮我引荐了AeroFS的一位创始人(AeroFS是一家YC投资的做P2P文件同步/共享的startup)。这大概就是所谓绝处逢生吧……

Facebook第二次技术电话面试的面试官仍然是中国人。走到这一步,之前的训练效果开始显现,基本上找到快速搞定这类入门级算法题的窍门和感觉了。这一轮面试也比较顺,和之后进行的Amazon第二次电面类似,四十五分钟连切三题,第三题也是因为时间关系只需讲思路。面试官听上去比较满意。面完之后很兴奋,心想这下至少能去Menlo Park溜达一圈了,就算面试没通过,也权当是参加电话竞猜中了个加州三日游了——没想到最后真被我乌鸦嘴说中,唉!第二天便收到了HR的onsite邀请,然后便开始办签证。


签证

Cat曾经在某群内说过一句话,大致是说“某些人整天说要出国,却连个旅游签证都不肯办”。好吧,看到这句话的时候我就有种躺枪的感觉——此前我还从未办过签证。收到onsite邀请时已经是二月中旬,为了赶上4月1日的H1B申请,HR敦促我务必尽快完成面试。收到Facebook用于办理B1商务签证的邀请函后,紧张的签证准备工作就开始了:准备材料、填写DS160表格、预约面签,各种头大,按下不表。

非常幸运的是,我预约到一个非常近的面试时间,这样一来三月初便可以抵达Menlo Park。由于去年八月份已于百度离职,我不禁担心会否因为当前没有雇主而导致面签被拒。为此,准备了户口本、结婚证、过往聘用合同、银行交易记录、学位证、毕业证等林林总总一大堆材料。不想面签当天这些材料一份都没有用到,美女面试官只询问了赴美目的和我所申请的职位的工作地点,期间在电脑上确认了一下我之前的工作经历,末了微笑着说了一句“Good luck”便放行了,整个过程不到30秒,连Facebook的邀请函都没有看。


Onsite

HR告知海外候选人的onsite面试一般安排成周五出发周一面试,中间隔一个周末,以便休息和倒时差,同时也尽量减少在职候选人请假的天数。我的onsite时间表也是如此。这个安排还是比较人性化的。不过事实证明短短一个周末是绝对倒不过来16个小时的时差——在美期间每天夜里都清醒得跟打了鸡血一样,完全没有睡意,以至于面试前一晚我只睡了不到四个小时,周一五场面试狂灌了四杯咖啡。今后再参加海外onsite恐怕得提前一个礼拜在家就开始倒时差才行。

Onsite前后,HR和负责协调旅社的Facebook工作人员都十分尽责,提供的信息十分详细。预订的酒店就是Cat面经中提到的Sheraton Palo Alto,地理位置极佳;缺点是网络龟速,恍如置身墙内,当时心想要是全美都这么个破网速,肉身翻墙又为哪般?

由于onsite是在总部进行,事先要签署一份NDA协议。协议内容十分严格,其中规定在面试期间获悉的任何information都属于保密范畴,所以我只会拣GlassDoor上涉及到的内容来写,面试中问答环节的内容就略过不提了(Facebook方面曾发邮件说欢迎到GlassDoor上写面经,所以这样做应该是安全的)。

Sheraton Palo Alto到Facebook总部大约20分钟车程。面试当天早上在酒店门口打车过去,在前台签到时大约是9:30,然后便是静候HR。期间连入Facebook的访客用无线网络上了会儿网,这才总算找回了对美帝网速的信心。十点钟帅哥HR准时现身,一番寒暄后便带我简单逛了一下园区,灌了杯咖啡。其中我最口水的是站立办公用的桌子和超大的显示器。其他细节各种面经都有介绍,按下不表。

面试在一个小号会议室进行,两面墙上都有答题用的白板。面试开始前,HR先介绍了各轮面试的内容和顺序。面试官分三种角色:

  • Ninja(忍者):面coding,白板写代码;
  • Jedi(星战里的绝地武士):面文化内容,诸如个人兴趣、职业规划等务虚内容;
  • Pirate(海盗):面系统设计。

我的面试安排是上午一轮ninja、一轮jedi加ninja、一轮pirate,下午两轮ninja。每轮45分钟。

第一轮ninja是个华人面试官。一共两道题,第一题先写出了一个正确但不太高效的解法;优化了一会儿,面试官勉强满意,进入第二题。第二题是道完全没见过的图论题,面试官题目描述到一半的时候我自以为想出一个很简单的做法,于是迅速说了思路,结果面试官也迅速给出了一个反例……来回两次之后面试官告诉我此路不通,挣扎了一会儿仍然没思路,最后终于时间到,不得不放弃。事后发现也是个经典问题,做不出来纯属复习不到位。这也是之前过于依赖LeetCode的恶果——LeetCode上的题目类型较窄,很多方面没有覆盖到。

第二轮是jedi加ninja,有两个面试官,一个负责面试,一个见习旁听。一上来先是jedi角色,聊了大约二十分钟,还算比较投机。余下的时间做了道题,一次性顺利通过。末了提问环节的时候聊到园区内各种涂鸦,顺手在白板上给旁听的面试官画了个漫画像(那位是光头,好画……)。

第三轮开始之前有十分钟中场休息时间,HR再次现身,又带我转了一圈,再灌一杯咖啡(困啊)。然后发生了一件比较坑爹的事情——面试官放鸽子了。我们回到会议室后,面试官并没有按时出现。又等了两分钟,HR出去打了个电话,叽哩咕噜了一会儿,然后一脸郁闷地骂了句“fuck”。原来面试官搞错了时间表,接电话时人还在家里……好在HR快速找到一位临时面试官,得以继续面试。虽然面试开始时间比预订时间晚了十五分钟,但这位临时面试官的表现却很专业。面完之后我自我感觉还不错。但事后才知道这一轮我的表现并不太好。原因有两个:第一,这是我这次求职过程中的第一轮也是唯一一轮系统设计面试,没有经验;第二,想太多了,一上来就往大数据上去想,从磁盘存储着手,没有及时发现面试官给出的数据量完全可以放入内存,面试官提示了几次才发现想复杂了(明明以前自己当面试官的时候还给候选人下过这个套的说)。

之后便是午餐。按惯例是由推荐人领候选人去餐厅,如果推荐人不在或没有推荐人,则由HR领去餐厅。我的推荐人当时正在国内,我本以为HR会过来,没想到发现Cat等在会议室门口。原来HR根据我简历上的背景资料给公司内可能认识我的人群发了邮件,希望找到熟人陪我吃午饭,而Cat在最后一分钟发现了这封邮件。由于我的日程是面试完毕后立即回国,没有时间游玩,所以事前基本没有通知在加州的同学和朋友,能见到熟人实在是意料之外的惊喜,让我对Facebook招聘工作的印象再次大大加分。午饭前后各一杯咖啡下肚,Cat又带我略逛了下园区,期间聊得十分愉快,感谢感谢!

下午是接连两轮ninja。第一轮是个欧洲口音的美女面试官。第一道题在第二轮电话面试中问过,告知之后换了一道,结果悲剧地卡在这道题上。题目本身不难,我也有思路。写到一半的时候面试官说这个算法占得空间太多,不够好,于是我试图按照她的思路走,结果自己没太想清楚,越走越绕,小错不断。眼看时间所剩无几,决定还是按照我原先的思路来,好歹先解出来,好坏再说。最后磕磕绊绊总算写出来。但这一轮只做了这么一道题,显然不理想。最后一轮又是两个面试官,一个主导一个旁听。这一轮的状况跟第二轮电话面试时差不多,非常顺,45分钟切了三道题,而且都写出了完整的代码。

第五轮结束后面试官直接将我送出了园区。本以为HR还会出现,打算再次道谢(整个招聘过程中他的工作确实非常出色),但最后没有见到。上午面试官放鸽子前就看他一副神色匆匆状,估计其他事情也忙得够呛。当时我还没有意识到上午最后一轮系统设计面试的评价不够高,心想除了上下午第一轮表现不好以外,其余三轮还不错,应该有胜算,于是心情还不错。

事后和Cat交流时了解到,一般onsite面试只安排四轮,如果四轮表现模棱两可,最后会加面一轮。但我的五轮面试是一早就确定好的,这点比较奇怪。我猜有可能是因为第一轮电话面试的结论比较模糊的缘故。


拒信

不知道是不是因为时差导致神智不清,我居然将机票上的出发时间1200PM错看成200PM,然后华丽丽地以误机画上了个人第一次国际旅行的句号……还好改签免费,不然可就亏大了(来回机票、住宿、餐饮、地面交通费用都是由Facebook报销的)。精疲力尽地回到北京之后,首都机场的Wifi死活连不上,回到家里立即查收邮件,于是就收到了拒信。不由得埋怨Facebook招聘工作未免太过高效了吧,各位面试官要不要再慎重考虑下啊?(哭……)不得不说当时还是相当沮丧的。HR在邮件中说可以另约时间沟通一下面试反馈的细节。考虑到onsite期间这位HR似乎工作非常繁忙,出于节约对方时间的考虑,回复邮件时我附上了一份用Google Docs做的在线问卷,其中列出了所有想问的问题,并尽量安排成了选择题的形式。同时,考虑到某些问题可能不方便作答,所有问题都设置成了选答题。

之后,不光收到了HR对问卷的答复,还收到了onsite面试官的反馈细节。由此我才得知系统设计面的反馈不佳。此外jedi面的反馈似乎很好,看来就算换了门语言,嘴皮子功夫也还是过得去的。总之,在决定性的面试官投票中我以一票之差落选。


小结

Facebook的面试从头到尾都如Cat所说的那样,没有高难度的题目,完全看基础是否足够扎实。我在电面和onsite面中出的状况全都是自己复习不到位或不够熟练所致。即便是系统设计题,也几乎不需要什么工作经验,我的感觉是比较优秀的应届生也不会有什么大问题,想得太多反倒容易栽跟头。

此外,如果不是Amazon反馈过晚,我应该还会在湾区再待上一两周,这样的话也许还来得及再争取一两家onsite面试机会。当然,Facebook onsite结束后我再次抱着侥幸心理盲目自信,没有下决心改签机票同样罪不可恕……

事后Facebook又发了一份在线调查问卷,对面试体验做调查,末了还提供了一份礼品清单,T恤、帽子、鼠标、记事本等等任选一样。总之从头到尾Facebook的招聘工作给我的感觉都很好,无论是工作质量、效率,还是人文关怀,都做得非常到位甚至超出预期。


后记

从最早萌生肉身翻墙的念头,到亲身实践一遍,再到机会擦身而过,感慨良多。不过,至少这次的经历证明了自己虽然功力还不够,但也差得不太多。我尚未放弃,准备充分之后还会再试一次。面试是个经验活儿。此次求职经历中,第一次电话面试、第一次跟老外交流、第一次系统设计面试等等,都表现不佳。此前虽然当了无数次面试官,面人没有一百也有几十,但轮到自己以候选人身份经历的求职面试却只有一次。如果之前不那么犹豫不决,在试Google之前多试几家积攒经验,结果可能就完全不一样了。

最后,跟同样有意向通过找工作翻墙的朋友们说一句:翻墙的可行性其实很高,只要技术和英语这两个硬指标过关,且家人不反对,再加上胆大心细,就很有希望。可惜我的例子不足以鼓舞人心,只能写点流水帐供大家参考罢了。

这篇面经欠了将近一个月,一方面是因为求职不顺心生懒散,一方面是blog主机服务商接连故障,前两天才完全恢复。今日终于把欠债补上了。



转载声明: 本文转自 加州求职记(cnblog)

原作者: 连城 (Lian, Cheng)



参考推荐:

去360还是留百度?

9个offer,12家公司,35场面试,从微软到谷歌

HR、技术高管和猎头眼中招聘那些事(CSDN)



    
最新技术文章:
▪Android开发之登录验证实例教程
▪Android开发之注册登录方法示例
▪Android获取手机SIM卡运营商信息的方法
▪Android实现将已发送的短信写入短信数据库的...
▪Android发送短信功能代码
▪Android根据电话号码获得联系人头像实例代码
▪Android中GPS定位的用法实例
▪Android实现退出时关闭所有Activity的方法
▪Android实现文件的分割和组装
▪Android录音应用实例教程
▪Android双击返回键退出程序的实现方法
▪Android实现侦听电池状态显示、电量及充电动...
▪Android获取当前已连接的wifi信号强度的方法
▪Android实现动态显示或隐藏密码输入框的内容
数据库其它 iis7站长之家
▪Android Touch事件分发过程详解
▪Android中实现为TextView添加多个可点击的文本
▪Android程序设计之AIDL实例详解
▪Android显式启动与隐式启动Activity的区别介绍
▪Android按钮单击事件的四种常用写法总结
▪Android消息处理机制Looper和Handler详解
▪Android实现Back功能代码片段总结
▪Android实用的代码片段 常用代码总结
▪Android实现弹出键盘的方法
▪Android中通过view方式获取当前Activity的屏幕截...
▪Android提高之自定义Menu(TabMenu)实现方法
▪Android提高之多方向抽屉实现方法
▪Android提高之MediaPlayer播放网络音频的实现方法...
▪Android提高之MediaPlayer播放网络视频的实现方法...
▪Android提高之手游转电视游戏的模拟操控
 


站内导航:


特别声明:169IT网站部分信息来自互联网,如果侵犯您的权利,请及时告知,本站将立即删除!

©2012-2021,,E-mail:www_#163.com(请将#改为@)

浙ICP备11055608号-3