2020.06 Java面试题汇总

最近找Java开发工作,面试了20多家,随着不断汲取前面面试经验,补充知识盲点,优化回答语言表达,后面面试拿到offer成功率大大提升,现把面试中问到的问题整理如下,希望对有需要的同行有所帮助,因为时间有限,答案后期整理了再逐步公布,目前先只提供问题。

2020.07.02鉴于小伙伴们强烈要求提供答案,但我目前时间有限,故对以下面试点进行粗略要点讲解,详细的还需要大家自己去查。

2020.07.03,多线程、类加载模块答案略解。

2020.07.05,jvm答案略解。

一、基础

1、字符串常量存储位置,new String()存储位置,==比较前面两种创建字符创结果,equals和==区别,字符串使用equals底层是怎么比较的。

String str1 = “abc”;

String str2 = “abc”;

String str3 = new String(“abc”);

String str4 = “a” + “bc”;

判断以下true or false

str1==str2

str1==str3

str1==str4

答案解析:

        (1)本题考查常量池位置(方法区)、对象位置(堆),==比较的是对象的地址,equals方法在于如何重新对象的equals方法,对于字符串,比较的是字符串的值,因为String的equals方法先比较的是字符创长度,再比较的是每个字符,完全相同才是true.

     (2) str1==str2为true,因为指向字符串常量池的同一个位置。str1==str3为false,以为方法区中内存地址不可能和堆内存地址相同,都不在一个位置。str1==str4为true,因为“a” + “bc”生成了一个新的对象"abc",在常量池中位置相同。

2、String不能被继承,为什么,能被改变吗?为什么?怎样才能被改变,StringBuilder和StringBuffer区别,string为什么要加final修饰?

       答案解析:

          (1)fianl修饰类、方法、变量。被fianl修饰的类不能被继承,final修饰的方法不能被重新,final修饰的常量不能被改变。

           (2)StringBuilder快但非线程安全,StringBuffer慢点但线程安全。

           (3)String被fianl修饰,主要考虑效率和安全性两个方面①final修饰的变量不能被修改,会安全些。②final修饰的字符串在常量池,如果存在,可以复用不必再new一个,提高效率,节省内存。

3、返回结果为多少,为什么

  int test(){

                 int x = 1;

                 try {
                         x=2;

                         return x;

                 } 

                 finally {

                  x=3;

                 }

}

    答案是;fianlly一定会执行,但返回值是2,不是3。对于本题,应该分两种方向考虑,如果return的是一个常量,在finally虽然执行,但不影响返回结果还是try后的结果,但是,如果是引用数据类型,譬如对象,结果会被影响,返回的是finally执行后的结果值。

4、既然Object是所有类的父类,说一下Object所拥有的方法及其用法。

    答案解析:Object中的方法为:finalize(手动垃圾回收调用)、wait(线程等待让处锁)、notify(唤醒其他线程)、notifyall(唤醒其他所有线程)、toString、clone(默认浅拷贝,深拷贝需要实现Cloneable接口)、equals(比较内容取决于如何重写该方法)、hashCode(计算hash值)

5、HashMap底层原理,初始化长度,扩容情况,安全(注意1.7和1.8区别)Hashtable、ConcurrentHashMap、

    答案解析:(1)Hashtable:线程安全,但不用,因为太慢。

                  (2)ConcurrentHashMap:线程安全,也比hashtable快,jdk1.7采用分段锁锁的包括多个HashEntry,1.8采用的锁是锁单个HashEntry,粒度更精细。

                 (3) HASHMAP扩容为什么是0.75(hash冲突最少,0.75只是个统计值,不同编程语言不同,但基本在0.75附近,)

                (4)什么是hash冲突,根据key可以计算出hashcode,不同的key可以计算出hashcode相同时,就冲突了。

                 (5)HashMap1.7用的数组加链表,1.8用的数组加链表加红黑树,当链表长度超过8变为红黑树。new HashMap时,没有指定长度,默认16,达到0.75负载时,2倍扩容,如果自己定义了,是2的n次方,则为该值,如果为非2的n次方,则比该数大的最近该数的2的n次方。

6、ArrayList底层,初始化长度,扩容,ArrayList和LinkedList内存情况区别

         答案解析:(1) LinkedList:底层是双向链表,链表的特点是增删快,查找慢。

                           (2)Vector:安全,但效率低,不用。

                           (3)ArrayList:底层是数组,可以通过下标索引查,故查询快,增减了某个位置数据,会造成后面所有数据移动,故增删慢。

                         (4)相同长度时ArrayList比LinkeList节省内存

                           (5)ArrayList扩容机制,定义后为0,第一个add方法后长度为10,超过10,每次增加1.5倍扩容。

         7、金融项目处理钱用的是Bigdecimal,底层是字符串处理

                 答案解析:一般鉴别是否做过金融项目的标准就是问算钱的数据类型用的什么,一般是进制用float、double的,因为他们不是精确地,会出现误差。Bigdecimal用来定义金钱数据类型,如果仅仅保存,不涉及到计算,当然字符串也行。

         8、介绍一下访问者模式(这个有兴趣的自己查吧)

         9、字节和字符区别,使用

                字节流一般用于读取文件图片文档,字符用于读取文本,文本也可以用字节流读取。

         9、数据加密RSA非对称,签名,对称AES,MD5

        答案解析:对于RSA,记住口诀:公钥加密,私钥解密;私钥签名,公钥验签,工作中都有现成的工具类生公私钥对,加解密方法,验签方法;AES是对称加密,MD5一般用于登录密码加密。

二、多线程

1、多线程CAS是什么(Compare and Swap),synchronize是什么,区别。

答案解析:CAS是乐观锁的一种常见操作,属于轻量级锁,知道VON操作,优缺点。synchronize属于重量级锁。

         2、Synchronize关键字用法,底层原理。

答案解析:synchronize本质是锁的对象,可以修饰三种位置:静方法、普通方法、代码块,面试会问三种区别,静态方法锁的对象是静态方法所在的类,普通方法是调用方法的new的对象,代码块就是自己选择的对象了。再有就是问到synchronize怎实现,这个回答是其基于操作系统的监视器了,知道使用时在对象头中加monitorenter,使用完了调monitorexit。

         3、锁的粒度:就是锁的范围大写的区别。

         4、Lock用法,和synchronize区别。

答案解析:(1)lock是Java API提供的锁,而synchronize是java语言本身带的锁,(2)lock需要手动加锁释放锁,unlock时要放在finally中,否则可能会死锁,synchronize自定释放锁,(3)lock使用时可以通过尝试获取锁,获取到执行锁,获取不到可以在else分支中执行其他逻辑,但synchronize就不行了。(4)都可以锁代码块,但synchronize还可以用于方法。

         5、volitale关键字作用,run和start区别,停止线程用什么(interupt,不用stop)

答案解析:(1)volitale不能保证原子性,但可以保证可见性、有序性,有序性是因为volitale会禁止指令重排。(2)run是线程中的方法,写代码逻辑,start是启动线程。(3)stop是让线程强制抛出异常,终止,可能会逻辑没执行完,废弃,interupt是通知险种终止,但不一定马上终止,安全。

         6、三种实现方式

答案解析:继承Thread类,实现Runnable、Callable接口。

         7、线程状态,每种状态能够语言表述其状态:

答案解析:新建状态(New)、就绪状态(Runnable)、运行状态(Running)、阻塞状态(Blocked)、死亡状态(Dead)。

         8、线程池有几种,都哪几种,有啥特点

答案解析:线程池有五种,Single Thread Executor、Cached Thread Pool、Fixed Thread Pool、Scheduled Thread Pool、Single Thread Scheduled Pool,作用自己查一下,记记。

      9、notify、notifyall、wait、sleep作用:

   答案解析:notify唤醒其他线程,notifyall唤醒其他所有线程,wait是当前线程让出锁,处于等待状态,sleep不会让出锁,休眠时间到了继续执行。

三、类的加载

         1、什么时候会加载类。

      答案解析:类加载的几种情况:(1)子类在加载时会把父类加载了,(2)new 对象时会把类加载了。(3)静态方法变量使用时会把类加载了。(4)main方法在执行时,会把自己所在类加载了。

         2、类的加载流程,及每步作用。(加载、验证、准备、解析、初始化、使用、卸载)

答案解析:(建议先自己查,理解全过程,但面试时间有限,可以根据情况选择回答的深度)加载就是把class加载到内存,验证就是验证是否符合语法规则,准备是放到方法区,解析是符号引用替换为直接引用,初始化是给变量赋值,使用就是执行逻辑,使用完了卸载。

         3、三种加载类,关系,作用,双亲委托机制

   答案解析:启动类加载器、扩展类加载器、应用类加载器。双亲委托是先找启动类加载器,找不到启动类,再找扩展类,扩展了还找不到,就找应用类加载器了。

四、jvm

         1、内存模型(类加载器、运行时数据区、执行引擎、本地方法接口)

               答案解析:这个一般问两个点:类加载、运行时数据区,另外两个基本不问,类加载已经在上面讲到。运行时数据在下面讲。

         2、运行时数据区:分为5部分,2共享,3私有,每个部分存什么

              答案解析:(1)运行时数据包括共享的方法区、堆,线程私有的java虚拟机栈、本地方法栈、程序计数器。

                                (2)线程私有:①程序计数器:记录代码运行的位置,线程切换后再切回来时,能够知道执行的位置。②本地方法栈:这个一般是调用其他语言用的。③java虚拟机栈:存储和方法相关的数据,譬如方法出口,入口,本地变量等。

                                (3)线程共享:①方法区:存放和类相关的数据,譬如静变量,静态方法,常量池。②堆:对象保存的位置,new的对象在此位置。

         3、判断对象是否可回收:可达性分析、程序计数法,区别,优劣,现在虚拟机用的哪个

             答案解析:可达性分析是类的根路径往下找,如果能找到,则为在使用状态,不回收,如果找不到,则为非使用状态,进行垃圾回收。程序计数法是是对象使用在对象头中标记数加一,结束调用则减一。现在虚拟机用的是可达性分析法。

         4、堆内存分区(年轻代(Eden、survivor0、survivor1)、老年代),这两个区内存回收算法(复制算法、标记清除、标记整理),算法内容优劣。

        答案解析:(1)1.8的jvm分为年轻代和老年代,年轻代包括Eden、survivor0、survivor1,采用的复制算法进行垃圾回收,老年代用的标记清除和标记整理算法。

         (2)复制算法把内存分为两等份,一份在使用,另一份在等待,回收时将存活的复制到空着的那份,另一份清空,缺点是浪费内存,所以使用与新生代,因为新生代的对象特点是朝生夕死,存活时间不会太长。

           (3)标记清除算法是将要回收的进行标记,然后回收,存在问题是造成内存碎片化。

            (4)标记整理是将不需要回收的进行复制到另外位置时,是连续布置,不会产生内存碎片化。

         5、G1垃圾回收算法,了解(最新的垃圾回收算法是G1,他们能保证垃圾回收时低延时)

        6、jvm调优

           答案解析:根据也许需要,改变虚拟机运行时内存不同区域的大小分配,可以通过参数配置改变。

         7、分析内存的工具:jdk的bin下的:

                  Jconsole:看堆、cpu情况,cpu时配合linux的top命令,jps看进程

                  Jmap快照看堆情况

         8、调整内存参数:主要有

                  方法区:-Xss

                  堆:-Xms、-Xmx

        

五、spring

         1、加载类到spring容器的方式

             答案解析:一种是Spring方式,通过配置文件,配置在web.xml,一种是SpringBoot方式,通过注解加载进spring容器,启动类上的SpringBootApplication注解,在加上类上的Component注解,Bean注解,通过Autowire或者Resource引入调用。

         2、springboot的常用注解

           答案解析:

@SpringBootApplication、@MapperScan("net.xdclass.xdvideo.mapper")、@Component、@RestController、@Service、@Mapper、@Autowired、@Resource.

         3、aop、ioc

           答案解析:aop是面向切面编程,用的是动态代理和反射,常用的地方是事务、日志。ioc是控制反转,用的是工厂模式,通过两种方式可以将对象在项目启动时加载到内存,一是配置文件方式,在web.xml中配置,而是通过注解方式,启东时将有@Component、@Bean注解的类加载到内存。

         4、动态代理:jdk的动态代理、cglib的动态代理区别
           答案解析:Jdk动态代理:利用拦截器(必须实现InvocationHandler)加上反射机制生成一个代理接口的匿名类,在调用具体方法前调用InvokeHandler来处理,Cglib动态代理:利用ASM框架,对代理对象类生成的class文件加载进来,通过修改其字节码生成子类来处理。

         5、反射

           答案解析:反射可以拿到类的所有属性方法,包括私有的和非私有的。

         6、springboot的starter的工作原理,常用的start方法

         7、项目中用到的定时器,有哪些,怎么用的

           答案解析:一个是quartz,一个是springboot@EnableScheduling方式。

六:springMVC

  1. 执行流程

          答案解析:请求在前端控制器、处理器映射器、处理器适配器、modelandview、视图解析器之间的执行流程。

     2.默认单实例多线程      

     3、HttpServletRequest获取参数是不安全的,为什么,怎么解决。

    答案解析:可以通过@Scope("prototype")实现多例解决线程安全问题,或者方法加锁,或者放到Threadlocal中保证每个线程内。

七:算法:

         1、栈特点,堆特点

            答案解析:堆的特点是先进后出,栈的特点是先进先出。

         2、如何用两个栈模拟队列(pust方法、pop方法)

           答案解析:用堆的操作模拟栈,要用到pop函数获取顶部数据,push压栈。

         3、斐波那契问题

           答案解析:这个是常问的算法,建议百度掌握一下。

         4、二分搜索求根5的值,精确到小数点后5位。

八:中间件;知道其中的几种

   1、Redis、memcache

        redis存储数据结构5中,memcache只有一种字符串,redis字符串最大是512M,mencache最大是1M。

   2、Redis的五种数据结构是什么,其中的zset怎么实现的(跳表)

         字符串,hash,列表,set,zset。zset是跳跃链表方式实现的。

     3、Redis为什么快

        主要是因为 Io多路复用,其次是基于内存,采用hashmap类似的keyvalue形式存储。

      4、如何将数据库数据缓存到redis:

            定时器、手动、方法中同步、中间件(阿里的canal监听数据库日志catlog)

       5、REDIS的缓存击穿,雪崩

            可以采用加锁方式,放入消息队列中,设置短暂的失效时间(一般5分钟左右)

       6、集群

       7、MQ用过哪些,怎么用,怎么配置

            队列一般有点对点模式,发布订阅模式,可以利用队列做异步,肖锋。

      8、ES

            搜索可以说solar,es,lucen

      9、Ngix

      10、Zookeper

       11、Kafuka

九:分布式微服务

  1. springcloud五大组件,每个组件的作用使用
  2. 分布式锁
  3. 分布式事务
  4. 分库分表

十:事务

  1. 什么是事务

2、四个特性

3、隔离级别

4、传播机制(还会问嵌套异常时回滚情况)

5、如何使用(配置文件、注解(注解上的参数有哪些))

6、能加try catch 吗?为什么?什么异常事务可以回滚?非运行时异常怎么也能回滚?

7、声明式事务、编程式事务

十一:Sql
     1、慢查询定位

         2、执行计划

         3、索引,作用,数据结构,二叉树,红黑树,BTree、B+Tree集中数据结构的区别

         4、联合索引,失效情况。

         5、索引使用规范(like模糊查询,什么情况下失效,什么情况不失效)

         6、常用的sql函数,其中to_date怎么用

         7、保险项目有问存储过程的

         8、in最多能支持1000条,如何解决

         9、mysql有几种执行引擎,其中innodb和myasam必须掌握特点和区别

         10、用过的数据源

         11、mysql、oracle、db2分页怎么处理

十二:体现个人解决问题思路:

  1. 遇到过什么问题,怎么解决的。
  2. 业余,下班,自己在学习什么,达到什么水平,解决什么问题。
  3. 开发过程中遇到的性能优化的经验,代码开发规范

         (1)性能优化,可以冲sql优化角度说。

          (2)复杂逻辑要有注释、sql关联查询一般不超过3个(关联太多效率低)、for循环处理数据库用mybatis的foreach标签,避免在java代码for循环中重复调用、代码过长封装方法......

     4.自己表擅长的

         java后台开发

     5.怎么统计当前在线人数

       登录后会在redis中存token数据,可以定时过滤reids中token的数量,来确定登录的人数。

     6.对出差怎么看的

        根据自己实际情况说,譬如我,短期可以,长期不太能接受。

      7.自己职业规划,未来发展

         技术、管理

十三:前端(因为我能做管理平台的简单页面,所以会简单问下前端)

  1. Ajax调用,ajax包含哪几部分。

        可以设置请求方式、url、数据格式、返回值包括正常和错误情况,根据返回结果进行判断添加自己逻辑。

  1. 前后端交互json时用到的几个注解,作用

         @RequestBody、@ResponseBody、@Restcontroller(是@Controller基础上加了@ResponseBody)

  1. 如何实现跨域

           后端配置、jsonp、nginx代理

十四:

         常用linux命令,查看日志,查找单词、输出

      1.常用命令:mkdir(创建文件夹)、tail -f 动态查看日志、cat看日志、(rm -rf)删除文件、ps -ef | grep java 查看包含“java”的所有进程、grep "java" info.log(在文件info.log中查找包含java字符串的行)、grep "java" info.log > out.log(在info.lo文件查找java字符并输出到out.log文件)

你可能感兴趣的:(Java,面试,java)