您的位置 首页 java

java 常见笔试题 (二)

1. 进程和线程有什么区别?用户线程和守护线程有什么区别?如何创建 守护线程

答: 一 个进程是一个独立(self contained)的运行环境,它可以被看作一个程序或者一个应用。而 线程 是在进程中执行的一个任务。 Java 运行环境是一个包含了不同的类和程序的单一进程。线程可以被称为轻量级进程。线程需要较少的资源来创建和驻留在进程中,并且可以共享进程中的资源。

当我们在Java程序中创建一个线程,它就被称为用户线程。一个守护线程是在后台执行并且不会阻止 jvm 终止的线程。当没有用户线程在运行的时候, JVM 关闭程序并且退出。一个守护线程创建的子线程依然是守护线程。

Thread.setDeamon(true)

2. Spring框架 中的三大核心思想是什么,并举例说出2个 Spring 中用到的设计模式

答: 三大核心思想:IOC 反转控制,DI 依赖注入, AOP 面向切面

用到的设计模式:简单工厂(spring上下文bean创建), 工厂方法(例如spring配置文件中通过factory-method 指定静态方法来创建bean ), 单例(Spring默认bean均为单例),代理(如使用动态代理实现AOP),观察者(如ContextLoaderListener),策略,模版方法(如 jdbc Template)等,装饰器(如使用AOP织入新逻辑)

3. AOP有哪些使用场景,底层是如何实现的

答: 应用场景:日志记录,性能统计,安全控制,事务处理, 异常处理

实现AOP的方法: 1 动态代理(运行期间) 2 动态字节码生成(使用cglib) 3 自定义类加载器 4 使用java Instrumentation特性,在 字节码 加载到jvm前进行字节码转换

4. 解释什么是 XSS 和CSRF

答: XSS:跨站脚本(Cross-site scripting)是注入攻击的一种。其特点是不对服务器端造成任何伤害,而是通过一些正常的站内交互途径,例如发布评论,提交含有JavaScript 的内容文本。这时服务器端如果没有过滤或转义掉这些 脚本 ,作为内容发布到了页面上,其他用户访问这个页面的时候就会运行这些脚本。

CSRF:跨站请求伪造(Cross-site request forgery) 通过伪装来自受信任用户的请求来利用受信任的网站

5. 请简述 synchronized 和java.util.concurrent.locks. Lock 的异同, 为什么调用object.wait()和object.notify()的时候要持有object的锁, wait()与sleep()的区别

答:Lock接口比同步方法和同步块提供了更具扩展性的锁操作。他们允许更灵活的结构,可以具有完全不同的性质,并且可以支持多个相关类的条件对象。

它的优势有:

(1) 可以使锁更公平

(2) 可以使线程在等待锁的时候响应中断

(3) 可以让线程尝试获取锁,并在无法获取锁的时候立即返回或者等待一段时间

(4) 可以在不同的范围,以不同的顺序获取和释放锁

因为wait和notify在调用时会释放当前持有锁

Wait与sleep区别

Wait是Object方法,sleep是Thread方法,sleep不释放锁,只是暂停执行一段时间后继续运行。而wait会释放锁,何时运行取决于cpu调度。

6. ArrayList、Vector、LinkedList的存储性能和特性分别是什么

答:ArrayList和Vector都是使用数组方式存储数据,此数组元素数大于实际存储的数据以便增加和插入元素,它们都允许直接按序号索引元素,但是插入元素要涉及数组元素移动等内存操作,所以索引数据快而插入数据慢, Vector 由于使用了synchronized方法(线程安全),通常性能上较ArrayList差,而LinkedList使用双向链表实现存储,按序号索引数据需要进行前向或后向遍历,但是插入数据时只需要记录本项的前后项即可,所以插入速度较快。

7. 请简述 cookie SESSION 区别与联系

答: 区别

(1) cookie是保存在浏览器的内存中,而 session 则是保存在服务器端。

(2) Session 与cookie相比,当你登陆访问页面的时候,使用 Cookie 可以自动登录,如果有人另外一个客户端同时登录。这个时候,服务器就会检查其session ID。如果已经有相同的session ID登录,就不会允许再登录。这样可以防止同一用户多次登录,保障公司的利益。

(3) 用户可以通过在浏览器设置不保存cookie,而当用户登录时,服务器会将session ID以密文的形式写在HTTP的响应报头,从而实现访问的上下连贯。

(4) cookie放置在浏览器内存中,使用起来更加灵活方便,session会在一定时间内保存在服务器上。当访问增多,会比较占用你服务器的性能

(5) SESSION是保存在服务端的;Cookie是保存在客户机器上的Session不可伪造;Cookie可以伪造!并且session不传递,因此,session比cookie更加的安全。

联系

二者都可以用来保存用户的信息, Session的使用要求用户浏览器必须支持Cookie,

如果浏览器不支持使用Cookie,或者设置为禁用Cookie,那么将不能使用Session。用户在进行访问时,服务器会通过查找session,将用户的session ID传给浏览器,而浏览器则将这个ID以cookie的形式保存在浏览器的内存中。也可以说cookie是session在浏览器中的标识。当然也可以以其他的方式保存

8. 写出几个常见的 http状态码

答: 举例如下,不限于以下结果:

200 OK //客户端请求成功

400 Bad Request //客户端请求有语法错误,不能被服务器所理解

401 Unauthorized //请求未经授权,这个状态代码必须和WWW-Authenticate报头域一起使用

403 Forbidden //服务器收到请求,但是拒绝提供服务

404 Not Found //请求资源不存在,eg:输入了错误的URL

500 Internal Server Error //服务器发生不可预期的错误

503 Server Unavailable //服务器当前不能处理客户端的请求,一段时间后可能恢复正常

9. 什么是浅拷贝和深拷贝,java中如何实现深拷贝

答: 浅拷贝是指拷贝对象时仅仅拷贝对象本身(包括对象中的基本变量),而不拷贝对象包含的引用指向的对象。深拷贝不仅拷贝对象本身,而且拷贝对象包含的引用指向的所有对象。

Java实现深拷贝的方法:1 重写clone方法 2 序列化后解序列化

10. 简述java堆内存与栈内存的区别与联系, Static 变量存储在哪里

答: 在函数中定义的 一些 基本类型的变量和对象的引用变量都是在函数的栈内存中分配。当在一段代码块中定义一个变量时,java就在栈中为这个变量分配内存空间,当超过变量的作用域后,java会自动释放掉为该变量分配的内存空间,该内存空间可以立刻被另作他用。

堆内存 用于存放由new创建的对象和数组。在堆中分配的内存,由 java虚拟机 自动垃圾回收器来管理。在堆中产生了一个数组或者对象后,还可以在栈中定义一个特殊的变量,这个变量的取值等于数组或者对象在堆内存中的首地址,在栈中的这个特殊的变量就变成了数组或者对象的引用变量,以后就可以在程序中使用栈内存中的引用变量来访问堆中的数组或者对象,引用变量相当于为数组或者对象起的一个别名,或者代号。

引用变量是普通变量,定义时在栈中分配内存,引用变量在程序运行到作用域外释放。而数组&对象本身在堆中分配,即使程序运行到使用new产生数组和对象的语句所在地代码块之外,数组和对象本身占用的堆内存也不会被释放,数组和对象在没有引用变量指向它的时候,才变成垃圾,不能再被使用,但是仍然占着内存,在随后的一个不确定的时间被垃圾回收器释放掉。这个也是java比较占内存的主要原因,实际上,栈中的变量指向堆内存中的变量,这就是 Java 中的指针!

Static变量存储在静态区中

11. 什么是 Restful , 如何使用Spring实现restful

答: 表现层状态转移,用url标识一个资源,用http四种请求POST,DELETE,PUT,GET代表增删改查

Controller使用PathVariable注解绑定url中的变量,RequestMapping中method代表具体操作类型(POST,DELETE,PUT,GET),整体以json格式传输数据给前端展示

12. 解释并对比 并行和并发,同步和阻塞

答: 并发的实质是一个物理CPU(也可以多个物理CPU) 在若干道程序之间多路复用,并发性是对有限物理资源强制行使多用户共享以提高效率。

并行性 指两个或两个以上事件或活动在同一时刻发生。在多道程序环境下,并行性使多个程序同一时刻可在不同CPU上同时执行。

阻塞是指当操作系统存在对内核调用时,操作系统将数据从内核加载到用户缓冲区这个过程中发生的等待。同步是指数据从用户缓冲区数据加载完成到用户进程去缓冲区取数据这个阶段发生的等待

13. 解释violate的作用,解释什么是CPU伪共享

答: Java语言提供了一种稍弱的同步机制,即volatile变量,用来确保将变量的更新操作通知到其他线程。当把变量声明为volatile类型后,编译器与运行时都会注意到这个变量是共享的, 因此不会将该变量上的操作与其他内存操作一起重排序。 volatile 变量不会被缓存在寄存器或者对其他处理器不可见的地方,因此在读取volatile类型的变量时总会返回最新写入的值。

缓存系统中是以缓存行(cache line)为单位存储的,当 多线程 修改互相独立的变量时,如果这些变量共享同一个缓存行,第一个线程已经修改了共享缓存行数据,后续线程操作该缓存行时数据实际已经失效,导致无法做到真正的并行,无意中影响彼此的性能,这就是伪共享。

14. 什么是集群脑裂,如何解决集群脑裂问题

答: 集群的脑裂通常是发生在集群中部分节点之间不可达而引起的(或者因为节点请求压力较大,导致其他节点与该节点的心跳检测不可用)。当上述情况发生时,不同分裂的小集群会自主的选择出master节点,造成原本的集群会同时存在多个master节点。

解决方案

1、踢出集群

(1) Quorum [‘kwɔːrəm] Algorithm

Quorum Algorithm(选举算法):集群内各节点通过心跳收集彼此的健康状况,收集到一个 心跳 就获得一票,假设集群内3个节点(A、B、C),节点A获得B和自己一票,节点B获得自己和A一票,而节点C只有自己,则节点C被踢出集群。

(2) Quorum Device

Quorum Algorithm有个缺陷:集群内如果只有2个节点,那就悲剧了。因此,需要引入第3个设备来解决此问题,此时,Quorum Device粉墨登场

Quorum Device(Quorum Disk):这个设备也占一票,这一票由先到请求者获得,这样就能顺利的踢出另一个节点。

2、IO隔离

节点虽然被踢出,但是仍然有可能处于active状态,这样,这家伙还能操作共享文件资源,危机依然挥之不去。银弹来了,IO隔离(IO Fencing)可以阻止” 灰太狼 羊村 “。

IO Fencing主要有两种方式,分别如下:

(1) 硬件方式

(A) SCSI Reserve/Release设备

正常节点能够使用SCSI Reserve/Release命令锁住存储设备,不正常节点发现存储设备被锁后,就用suicide(自杀)的方式来了结自己以使自己恢复正常。

(B)STONITH(Shoot The Other Node In The Head)

当一个节点发生故障时,另一个节点如果检测到了,就会通过串口来控制故障节点的电源开关以暂时断电然后又上电来重启故障节点。手好黑啊,好在还没彻底落井下石。

(2) 软件方式

ORACLE RAC 就是典型代表,直接重启故障节点以保证故障节点不能继续访问共享数据。

15. 一致性Hash算法解决了什么问题?

答:在分布式集群中,对机器的添加删除,或者机器故障后自动脱离集群这些操作是分布式集群管理最基本的功能。如果采用常用的hash(object)%N算法,那么在有机器添加或者删除后,很多原有的数据就无法找到了,这样严重的违反了单调性原则。( 单调性是指如果已经有一些内容通过哈希分派到了相应的缓冲中,又有新的缓冲区加入到系统中,那么哈希的结果应能够保证原有已分配的内容可以被映射到新的缓冲区中去,而不会被映射到旧的缓冲集合中的其他缓冲区)

16. 简要描述以下 加密算法 并给出典型的算法

(1) 数字摘要

(2) 对称加密

(3) 非对称加密

答: (1) 数字摘要:将任意长度的消息变成固定长度的短消息,常用的加密算法包括 HASH (MD5 、SHA1 、SHA256)、HMAC(HmacMD5/HmacSHA1/HmacSHA256)等

(2) 对称加密:采用单钥 密码系统 的加密方法,同一个 密钥 可以同时用作信息的加密和解密,这种加密方法称为对称加密,也称为单密钥加密。 常用的有:3DES,AES

(3) 非对称加密:非对称加密算法需要两个密钥:公开密钥(publickey)和私有密钥(privatekey)。公开密钥与私有密钥是一对,如果用公开密钥对数据进行加密,只有用对应的私有密钥才能解密;如果用私有密钥对数据进行加密,那么只有用对应的公开密钥才能解密。因为加密和解密使用的是两个不同的密钥,所以这种算法叫作非对称加密算法。 常用的有: RSA

17. 举例说明spring boot中的核心启动主函数(main函数)常用的注解以及注解的作用.

答: @SpringBootApplication . 作用:用于标识声明一个springboot框架容器.

@EnableAsync 开启spring异步任务支持

@EnableCaching 开启缓存支持

@EnableScheduling 开启定时任务

@EnableTransactionManagement 开启事务支持

18. 简述 Tomcat 以下配置的作用:protocol, maxThreads, acceptCount, maxConnections, connectionTimeout

答:

protocol

设置用于处理请求的协议。默认值是HTTP/1.1,在这种模式下是采用基于阻塞IO的连接器还是基于APR/native的连接器,tomcat采取了一种自动切换的机制。如果环境变量(Windows中的PATH、Linux中的LD_LIBRARY_PATH变量)包含Tomcat原生的库,则会采用APR/native连接器;如果环境变量不包含Tomcat原生的库,则阻塞IO的连接器会被使用。需要注意的是APR/native连接器在HTTPS设置上与Java连接器不同。

如果要显示指定协议而不是依赖于前文中描述的自动机制,有以下协议可供选择:

org.apache.coyote.http11.Http11Protocol – 阻塞java连接器 org.apache.coyote.http11.Http11NioProtocol – 非阻塞java连接器 org.apache.coyote.http11.Http11AprProtocol – APR/native连接器

maxThreads

连接器可以创建的用于处理请求的最大线程数量,决定了可以同时处理请求的最大数量。如果没有指定,默认是200个线程。如果当前连接器关联了一个 Executor , 这个属性就会被忽略掉,因为连接器会使用Executor来执行任务而不再使用内部的线程池。

acceptCount

如果所有的tomcat线程被占用了最大缓冲的连接请求数。如果该队列满了,则所有新来的连接请求会被拒绝,默认值是100。

maxConnections

任何时候server可以接受的最大连接数。如果这个最大值达到了,新来的请求会被缓冲到请求队列中(使用acceptCount参数指定队列大小),直到连接数将至maxConnections数以下,新来的请求才会被接受并处理。此默认值随着连接器的类型有所差别,比如BIO默认值是maxThreads数(BIO方式每个连接是一个线程)、NIO默认值是10000(NIO方式每个线程可以同时处理多个连接,具体请查询NIO IO多路复用的原理)、APR/native默认值是8192。

值得注意的是在Windows系统中,如果采用APR/native连接器,处于性能的考虑这个值会被降低为最邻近的1024的整数倍。

如果设置为-1,maxConnections设置会被禁用并且连接不会被计数。

connectionTimeout

连接超时时间,默认为60000ms(60秒)

文章来源:智云一二三科技

文章标题:java 常见笔试题 (二)

文章地址:https://www.zhihuclub.com/189236.shtml

关于作者: 智云科技

热门文章

网站地图