今天电面了阿里,才知道自己有多菜。。。。
还有很多事情需要系统化,整理成一套理论知识,
不能掌握了皮毛就以为自己666了。。。
除了实践出真知,还要明白,知识是前进的灯塔,积累绝不会白费的。
今天做了好多猜猜乐,
但从今以后绝不会再在面试里,靠猜来回答问题。
电面清单:
面向对象语言的特点:
封装,继承,多态
面向对象和面向过程语言的区别:
面向过程
优点:性能比面向对象高,因为类调用时需要实例化,开销比较大,比较消耗资源;比如单片机、嵌入式开发Linux/Unix等一般采用面向过程开发,性能是最重要的因素。
缺点:没有面向对象易维护、易复用、易扩展
面向对象
优点:易维护、易复用、易扩展,由于面向对象有封装、继承、多态性的特性,可以设计出低耦合的系统,使系统 更加灵活、更加易于维护
缺点:性能比面向过程低
HTTP的报文格式:
一个HTTP请求报文由请求行(request line)、请求头部(header)、空行和请求数据4个部分组成,下图给出了请求报文的一般格式。
or
<request-line>
<headers>
<blank line>
[<request-body>
http如何通过url获取信息
1. 第一部分,是协议或称为服务方式 (指定低层使用的协议,例如:http, https, ftp);
2. 第二部分,是存有该资源的主机IP地址(有时也包括端口号);
3. 第三部分,是主机资源的具体地址。如目录和文件名等。
http响应和tcp三次握手:
TCP三次握手:
TCP通信过程包括三个步骤:建立TCP连接通道,传输数据,断开TCP连接通道。
http连接过程:
1 建立连接
先解析DNS,把localhost变成ip(127.0.0.1),然后根据127.0.0.1和端口号8080(没有端口号则使用默认的端口)建立socket。也可以理解为通过“三次握手”建立TCP连接,确定通讯正常。
2 发送请求命令
socket建立好之后,客户端开始向web服务器发送请求命令(GET/POST等)。
3 发送请求头(和请求正文如果有)
客户端先发送与自身相关的信息,再发送空行表示请求头发送完毕,如果是post则继续发送请求正文。
4 回传状态行
应答第一步,发送协议版本和状态码(200、503、404等)
5 回传应答头
应答第二步,先发送自身相关信息、Content-Type(必须)及被请求的文档,在发送空行宝石应答头发送完毕。
6 回传应答正文
应答第三步,根据应答头的Content-Type指定的格式发送应答正文。
7 关闭连接
一次‘会话’完成,如果设置了Connection:keep-alive则TCP连接不关闭,否则关闭连接。
java基本数据类型:(我真的没有想到这个我都答不出来)
虽然我隐约记得是八个…
int,float,double,long,short,boolean,char,byte
object的==和equal相同吗?
相同!
Object类,它是java中所有类的根类。Object类的子类都可以使用Object中定义的方法。
此次主要介绍Object类中定义的equals(Object obj)方法。
这个方法的作用是比较两个对象是否相等(而不是比较对象的属性是否相同)。
仅当被比较的两个引用变量指向同一个对象(即指向同一个地址),
该方法返回true,否则返回false。
这和操作符“==”用于比较引用变量时功能一样。
String a= “” 与 String a = new String()区别
1、’直接定义的String “a”'c’是储存在 常量存储区中的字符串常量池中;
new String(“a”)是存储在堆中;
2、常量池中相同的字符串只会有一个,但是new String(),
每new一个对象就会在堆中新建一个对象,不管这个值是否相同;
String a = “a” String b = “a” a b都指向字符串常量池中的“a”,所以 a==b 为 true;
String a = new String(“a”) String b = new String(“a”);
是会在堆中创建两个对象new String() “a”是常量池中的”a”,
这两个对象的值都为 a,所以a==b 返回false;a.equals(b)返回true;
3、
String a = “a”在编译阶段就会在内存中创建;
String a = new String(“a”);是在运行时才会在堆中创建对象
String类型对象创建个数,(均不考虑字符串在常量池中已存在的情况):
1 String a="123";
创建了1个对象
jvm在编译阶段会判断常量池中是否有 "123" 这个常量对象如果有,
a直接指向这个常量的引用,
如果没有会在常量池里创建这个常量对象。
2 String a=new String("123");
创建了2个对象
同情况1,jvm编译阶段判断常量池中 "123"存在与否,进而来判断是否创建常量对象,
然后运行阶段通过new关键字在java heap创建String对象。
3 String a="123"+"456";
创建了1个对象
jvm编译阶段过编译器优化后会把字符串常量直接合并成"123456",
所有创建对象时最多会在常量池中创建1个对象。
4 String a="123"+new String("456");
创建了4个对象
常量池对象"123" ,"456",new String("456")创建堆对象,还有一个堆对象"123456"。
加锁的方法:
对象锁(方法锁),是针对一个对象的,
它只在该对象的某个内存位置声明一个标识该对象是否拥有锁,
所有它只会锁住当前的对象,一般一个对象锁是对一个非静态成员变量进行synchronized修饰,
或者对一个非静态成员方法进行synchronized进行修饰,对于对象锁,
不同对象访问同一个被synchronized修饰的方法的时候不会阻塞
类锁是锁住整个类,当有多个线程来声明这个类的对象时候将会被阻塞,
直到拥有这个类锁的对象呗销毁或者主动释放了类锁,
这个时候在被阻塞的线程被挑选出一个占有该类锁,声明该类的对象。
其他线程继续被阻塞住。
无论是类锁还是对象锁,父类和子类之间是否阻塞没有直接关系。
当对一个父类加了类锁,子类是不会受到影响的,相反也是如此。
因为synchronized关键字并不是方法签名的一部分,它是对方法进行修饰的。
当子类覆写父类中的同步方法或是接口中声明的同步方法的时候,
synchronized修饰符是不会被自动继承的,所以相应的阻塞问题不会出现。
注意:这里的阻塞问题是指的按照正常情况下应该阻塞,
而因为synchronized是父类与子类之间不可传递导致不会阻塞。
当一个子类没有覆盖父类的方法的时候,这时候通过子类访问方法则会产生阻塞。
插入一句:构造方法不可能是真正同步的(尽管可以在构造方法中使用同步块)。
你了解volatile吗
数据库的加锁方法:悲观锁乐观锁
数据库引擎的区别。
设计模式:
感谢面试官的33分钟,让我充分认识到读研和系统化自己的知识的必要性。一步一个脚印,希望能对大家有所帮助。