爱奇艺面试

winer 贡献于2017-11-23

作者 王伟男  创建于2017-10-09 11:10:00   修改者王伟男  修改于2017-10-10 08:56:00字数6758

文档摘要:
关键词:

爱奇艺面试: 1. Java的类支持多重继承吗? 这句话要看怎么理解去了,一个类不能直接继承两个类比如说这样: class A extends B,C 不能这样写,因为java不支持多继承, 但是你可以像下面这样实现继承多个类 class A extends B class C extends A 这样C就同时继承了B和A两个类 2. 进程与线程的关系与区别? 进程是表示资源分配的基本单位,又是调度运行的基本单位。例如,用户运行自己的程序,系统就创建一个进程,并为它分配资源,包括各种表格、内存空间、磁盘空间、I/O设备等。然后,把该进程放人进程的就绪队列。进程调度程序选中它,为它分配CPU以及其它有关资源,该进程才真正运行。所以,进程是系统中的并发执行的单位。 在Mac、Windows NT等采用微内核结构的操作系统中,进程的功能发生了变化:它只是资源分配的单位,而不再是调度运行的单位。在微内核系统中,真正调度运行的基本单位是线程。因此,实现并发功能的单位是线程。 线程是进程中执行运算的最小单位,亦即执行处理机调度的基本单位。如果把进程理解为在逻辑上操作系统所完成的任务,那么线程表示完成该任务的许多可能的子任务之一。例如,假设用户启动了一个窗口中的数据库应用程序,操作系统就将对数据库的调用表示为一个进程。假设用户要从数据库中产生一份工资单报表,并传到一个文件中,这是一个子任务;在产生工资单报表的过程中,用户又可以输人数据库查询请求,这又是一个子任务。这样,操作系统则把每一个请求――工资单报表和新输人的数据查询表示为数据库进程中的独立的线程。线程可以在处理器上独立调度执行,这样,在多处理器环境下就允许几个线程各自在单独处理器上进行。操作系统提供线程就是为了方便而有效地实现这种并发性。 引入线程的好处(1)易于调度。(2)提高并发性。通过线程可方便有效地实现并发性。进程可创建多个线程来执行同一程序的不同部分。(3)开销少。创建线程比创建进程要快,所需开销很少。(4)利于充分发挥多处理器的功能。通过创建多线程进程(即一个进程可具有两个或更多个线程),每个线程在一个处理器上运行,从而实现应用程序的并发性,使每个处理器都得到充分运行。 进程和线程的关系 (1)一个线程只能属于一个进程,而一个进程可以有多个线程,但至少有一个线程。线程是操作系统可识别的最小执行和调度单位。 (2)资源分配给进程,同一进程的所有线程共享该进程的所有资源。 同一进程中的多个线程共享代码段(代码和常量),数据段(全局变量和静态变量),扩展段(堆存储)。但是每个线程拥有自己的栈段,栈段又叫运行时段,用来存放所有局部变量和临时变量。 (3)处理机分给线程,即真正在处理机上运行的是线程。 (4)线程在执行过程中,需要协作同步。不同进程的线程间要利用消息通信的办法实现同步。 进程和线程的关系 一个线程可以创建和撤销另一个线程; 同一个进程中的多个线程之间可以并发执行.相对进程而言,线程是一个更加接近于执行体的概念,它可以与同进程中的其他线程共享数据,但拥有自己的栈空间,拥有独立的执行序列。 进程和线程的区别 进程和线程的主要差别在于它们是不同的操作系统资源管理方式。进程有独立的地址空间,一个进程崩溃后,在保护模式下不会对其它进程产生影响,而线程只是一个进程中的不同执行路径。线程有自己的堆栈和局部变量,但线程之间没有单独的地址空间,一个线程死掉就等于整个进程死掉,所以多进程的程序要比多线程的程序健壮,但在进程切换时,耗费资源较大,效率要差一些。但对于一些要求同时进行并且又要共享某些变量的并发操作,只能用线程,不能用进程。 优缺点 线程和进程在使用上各有优缺点:线程执行开销小,但不利于资源的管理和保护;而进程正相反。同时,线程适合于在SMP机器上运行,而进程则可以跨机器迁移。 3. 数据库的索引怎么理解 索引类似于字典的前面的查字表,把某个字段的数据从头到尾排序放在一起,并写明对应的数据记录的位置。这样搜索的时候只要翻这个就可以了,不需要从头到尾遍历数据 索引的原理:对要查询的字段建立索引其实就是把该字段按照一定的方式排序;建立的索引只对该字段有用,如果查询的字段改变,那么这个索引也就无效了,比如图书馆的书是按照书名的第一个字母排序的,那么你想要找作者叫张三的就不能用改索引了;还有就是如果索引太多会降低查询的速度 索引是优缺点:   首先明白为什么索引会增加速度,DB在执行一条Sql语句的时候,默认的方式是根据搜索条件进行全表扫描,遇到匹配条件的就加入搜索结果集合。如果我们对某一字段增加索引,查询时就会先去索引列表中一次定位到特定值的行数,大大减少遍历匹配的行数,所以能明显增加查询的速度。那么在任何时候都应该加索引么?这里有几个反例:1、如果每次都需要取到所有表记录,无论如何都必须进行全表扫描了,那么是否加索引也没有意义了。2、对非唯一的字段,例如“性别”这种大量重复值的字段,增加索引也没有什么意义。3、对于记录比较少的表,增加索引不会带来速度的优化反而浪费了存储空间,因为索引是需要存储空间的,而且有个致命缺点是对于update/insert/delete的每次执行,字段的索引都必须重新计算更新。所以并不是任何情况下都改建立索引的  聚集索引:该索引中键值的逻辑顺序决定了表中相应行的物理顺序。 聚集索引:确定表中数据的物理顺序。 聚集索引类似于电话簿,后者按姓氏排列数据。由于聚集索引规定数据在表中的物理存储顺序,因此一个表只能包含一个聚集索引。但该索引可以包含多个列(组合索引),就像电话簿按姓氏和名字进行组织一样。  非聚集索引:数据存储在一个地方,索引存储在另一个地方,索引带有指针指向数据的存储位置。 非聚集索引中的项目按索引键值的顺序存储,而表中的信息按另一种顺序存储(这可以由聚集索引规定)。对于非聚集索引,可以为在表非聚集索引中查找数据时常用的每个列创建一 个非聚集索引。有些书籍包含多个索引。例如,一本介绍园艺的书可能会包含一个植物通俗名称索引,和一个植物学名索引,因为这是读者查找信息的两种最常用的方法。 排序的复杂度 冒泡排序 1. public static void bubbleSort(int[] array) {   2.     int len = array.length;   3.     for (int i = 0; i < len; i++) {   4.         for (int j = 0; j < len - i - 1; j++) {   5.             if (array[j] > array[j + 1]) {   6.                 int temp = array[j + 1];   7.                 array[j + 1] = array[j];   8.                 array[j] = temp;   9.             }   10.         }   11.     }   12. }   直接插入排序 算法原理:插入排序的基本方法是:每步将一个待排序序列按数据大小插到前面已经排序的序列中的适当位置,直到全部数据插入完毕为止。  假设有一组无序序列 R0, R1, … , Rn−1:  (1) 将这个序列的第一个元素R0视为一个有序序列;  (2) 依次把 R1, R2, … , Rn−1 插入到这个有序序列中;  (3) 将Ri插入到有序序列中时,前 i-1 个数是有序的,将Ri和R0 ~ Ri−1从后往前进行比较,确定要插入的位置。 1. public static void insertSort(int[] array) {   2.     for (int i = 1, len = array.length; i < len; i++) {   3.         if (array[i] < array[i - 1]) {   4.             int temp = array[i];   5.             int j;   6.             for (j = i - 1; j >= 0 && temp < array[j]; j--) {   7.                 array[j + 1] = array[j];   8.             }   9.             array[j + 1] = temp;   10.         }   11.    12.     }   13. }   直接选择排序  算法原理:直接选择排序是一种简单的排序方法,它的基本思想是:  第一次从R[0]~R[n-1]中选取最小值,与R[0]交换,  第二次从R[1]~R[n-1]中选取最小值,与R[1]交换,  ….,  第i次从R[i-1]~R[n-1]中选取最小值,与R[i-1]交换,  …..,  第n-1次从R[n-2]~R[n-1]中选取最小值,与R[n-2]交换,  共通过n-1次,得到一个从小到大排列的有序序列。 1. public static void selectSort(int[] array) {   2.     int n = array.length;   3.     for (int i = 0; i < n; i++) {   4.         int minIndex = i;   5.         for (int j = i + 1; j < n; j++) {   6.             if (array[minIndex] > array[j]) {   7.                 minIndex = j;   8.             }   9.         }   10.         if (i != minIndex) {   11.             int temp = array[i];   12.             array[i] = array[minIndex];   13.             array[minIndex] = temp;   14.         }   15.     }   16. }   算法的稳定性定义为,对于待排序列中相同项的原来次序不能被算法改变则称该算法稳定. 直接选择排序算法,不稳定性,举个简单的例子,就知道它是否稳定..例如:(7) 2 5 9 3 4 [7] 1...当我们利用直接选择排序算法进行排序时候,(7)和1调换,(7)就跑到了[7]的后面了,原来的次序改变了,这样就不稳定了. 打印单链表中倒数第k个节点的数据 #include #include #include typedef struct aa{ int data; struct aa *next; } Dayink(int k,NODE *h){ NODE* p; p=h; int i=0; for(i=1;i<=10-k;i++){ p=p->next; } printf(“the data is: %d”,p->data); } Void main(){ NODE *h,*p,*s; int i; int k; scanf(“%d”,&k); h=p=( NODE *)malloc (sizeof (NODE )); for(i=1;i<=10;i++){ s=( NODE *)malloc (sizeof (NODE )); s->data=rand()%16; s->next=p->next; p->next=s; p=p->next; } p->next=NULL; Dayink(k,h); } V型表 一般来讲:单元测试所对应的是详细设计环节,也就是说,单元测试的测试用例是和详细设计一起出现的,在研发人员做详细设计的时候,相应的测试人员也就把测试用例写了出来;集成测试对应概要设计,在做模块功能分析及模块接口,数据传输方法的时候,就把集成测试用例根据概要设计中模块功能及接口等实现方法编写出来,以备以后作集成测试的时候可以直接引用;而系统测试,就是根据需求分析而来,在系统分析人员作系统分析,编写需求说明书的时候测试人员就根据客户需求说明书,把最后能实现系统功能的各种测试用例写出来,为做最后系统测试作准备。验收测试与用户需求对应,是非设计流程。 TCP协议中的三次握手: 第一次握手:Client通过发送一个TCP报文段向服务器发起连接请求,该报文段被称为SYN报文段。 第二次握手:该报文段被称为SYNACK报文段,顾名思义,这是Server对Client发送的SYN报文段进行确认(ACK),示意Client连接被允许。该报文段也不包含应用数据。  第三次握手:该报文段被称为ACK报文段,是Client对Server的应答进行确认(ACK),服务器成功收到ACK报文段之后,连接就建立成功了。  此时Syn的值被置为0;  TCP协议中的四次握手: 【注意】中断连接端可以是Client端,也可以是Server端。 第一次握手:假设Client端发起中断连接请求,也就是发送FIN报文。 第二次握手:Server端接到FIN报文后,意思是说"我Client端没有数据要发给你了",但是如果你还有数据没有发送完成,则不必急着关闭Socket,可以继续发送数据。所以你先发送ACK,"告诉Client端,你的请求我收到了,但是我还没准备好,请继续你等我的消息"。这个时候Client端就进入FIN_WAIT状态,继续等待Server端的FIN报文。 第三次握手:当Server端确定数据已发送完成,则向Client端发送FIN报文,"告诉Client端,好了,我这边数据发完了,准备好关闭连接了"。 第四次握手:Client端收到FIN报文后,"就知道可以关闭连接了,但是他还是不相信网络,怕Server端不知道要关闭,所以发送ACK后进入TIME_WAIT状态,如果Server端没有收到ACK则可以重传。“,Server端收到ACK后,"就知道可以断开连接了"。Client端等待了2MSL后依然没有收到回复,则证明Server端已正常关闭,那好,我Client端也可以关闭连接了。Ok,TCP连接就这样关闭了! 什么是 HTTPS? HTTPS (基于安全套接字层的超文本传输协议 或者是 HTTP over SSL) 是一个 Netscape 开发的 Web 协议。 你也可以说:HTTPS = HTTP + SSL HTTPS 在 HTTP 应用层的基础上使用安全套接字层SSL作为子层。 为什么需要 HTTPS ? 超文本传输协议 (HTTP) 是一个用来通过互联网传输和接收信息的协议。HTTP 使用请求/响应的过程,因此信息可在服务器间快速、轻松而且精确的进行传输。当你访问 Web 页面的时候你就是在使用 HTTP 协议,但 HTTP 是不安全的,可以轻松对窃听你跟 Web 服务器之间的数据传输。在很多情况下,客户和服务器之间传输的是敏感歇息,需要防止未经 授权的访问。为了满足这个要求,网景公司(Netscape)推出了HTTPS,也就是基于安全套接字层的 HTTP 协议。 HTTP 和 HTTPS 的相同点 大多数情况下,HTTP 和 HTTPS 是相同的,因为都是采用同一个基础的协议,作为 HTTP 或 HTTPS 客户端——浏览器,设立一个连接到 Web 服务器指定的端口。当服务器接收到请求,它会返回一个状态码以及消息,这个回应可能是请求信息、或者指示某个错误发送的错误信息。系统使用统一资源定位器 URI 模式,因此资源可以被唯一指定。而 HTTPS 和 HTTP 唯一不同的只是一个协议头(https)的说明,其他都是一样的。 HTTP 和 HTTPS 的不同之处 HTTP 的 URL 以 http:// 开头,而 HTTPS 的 URL 以 https:// 开头 HTTP 是不安全的,而 HTTPS 是安全的 HTTP 标准端口是 80 ,而 HTTPS 的标准端口是 443 在 OSI 网络模型中,HTTP 工作于应用层,而 HTTPS 工作在传输层 HTTP 无需加密,而 HTTPS 对传输的数据进行加密 HTTP 无需证书,而 HTTPS 需要认证证书 如何测试网页的登录页面 界面测试(UI Test) 1,界面设计风格是否与UI设计一致 2.界面中的文字简洁易懂,没有错别字,个别文字字体颜色 功能测试(Function test) 1.输入正确的用户名和密码,点击【登录】,验证是否能正确登录。 2.用户名和密码为空,点击【登录】,提示信息 3.输入用户名,密码为空,点击【登录】,提示信息 4.用户名和密码,如果太短或者太长,提示信息 5.用户名和密码,中有特殊字符,和其他非英文的情况,程序处理 6.用户名和密码大小写处理 7.用户名和密码前后空格的处理 8.密码是否加密显示 9.密码是否支持复制粘贴操作输入 10.是否支持Enter和Tab快捷键操作 性能测试(performance test) 1.打开登录页面,需要几秒 2.输入正确的用户名和密码后,登录成功跳转到新页面,不超过5秒 安全性测试(Security test) 1.登录成功后生成的Cookie,是否是httponly (否则容易被脚本盗取) 2.用户名和密码是否通过加密的方式,发送给Web服务器 3.用户名和密码的验证,应该是用服务器端验证, 而不能单单是在客户端用javascript验证 4.用户名和密码的输入框,应该屏蔽SQL 注入攻击 5.用户名和密码的的输入框,应该禁止输入脚本 (防止XSS攻击) 6.错误登录的次数限制(防止暴力破解) 7.登录成功后,长时间不操作,再次刷新页面后是否退出网站,跳转到登录页面 8.同一台电脑是否支持多个用户登录 9.一个用户是否能在多台电脑上登录 兼容性测试(Compatibility Test) 1.主流的浏览器下能否显示正常已经功能正常(IE,6,7,8,9, Firefox, Chrome, Safari,等) 2.不同的平台是否能正常工作,比如Windows, Mac 3.移动设备上是否正常工作,比如Iphone, Andriod 4.不同的分辨率 如何提交BUG: 缺陷报告的组成部分

下载文档到电脑,查找使用更方便

文档的实际排版效果,会与网站的显示效果略有不同!!

需要 10 金币 [ 分享文档获得金币 ] 0 人已下载

下载文档