欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

java面试题总结--基础篇

程序员文章站 2022-05-06 17:16:26
...

java 基础

1.八种基本数据类型的大小,以及他们的封装类

double    ---Double      8位        0.0d
float     ---Float       4位        0.0f
long      ---Long        8位        0L
int       ---Integer     4位        0
short     ---Short       2位        (short)0
byte      ---byte        1位        (byte)0
char      ---Character   2位        null\u0000
boolean   ---Boolean      --         false

2. 引用数据类型

数组,类,接口

3. Switch能否用string做参数

以前只能支持byte、short、char、int,可以强转
Jdk7.0以后可以,整型、枚举类型、boolean、字符串都可以

4. equals与==的区别*

== 比较的是2个对象的地址,而equals比较的是2个对象的内容
== 比较的是变量(栈)内存中存放的对象的(堆)内存地址,用来判断两个对象的地址是否相同,即是否是指相同一个对象。比较的是真正意义上的指针操作。
Equals用来比较的是两个对象的内容是否相等,由于所有的类都是继承自java.lang.Object类的,所以适用于所有对象,如果没有对该方法进行覆盖的话,调用的仍然是Object类中的方法,而Object中的equals方法返回的却是==的判断。

5. 自动装箱,常量池

自动装箱:基本数据类型---->对象类型
自动拆箱:对象类型---->基本数据类型
常量池:Byte,Short,Integer,Long,Character在自动装箱时对于值从–128到127之间的值(共享),会存在内存中被重用
字符串常量池
常量池在java用于保存在编译期已确定的,已编译的class文件中的一份数据。它包括了关于类,方法,接口等中的常量,也包括字符串常量,如String s = “java”这种申明方式;当然也可扩充,执行器产生的常量也会放入常量池,故认为常量池是JVM的一块特殊的内存空间。

6. Object有哪些公用方法

clone(),hashCode(),equals(),notify(),notifyAll(),wait(),getClass(),toString,finalize()

7. Java的四种引用,强弱软虚,用到的场景

强引用:使用普遍的引用,内存空间不足了,一般垃圾回收器绝不会回收它
软引用:软引用可用来实现内存敏感的高速缓存,内存空间不足了,就会回收这些对象的内存。
弱引用:具有弱引用的对象,不管当前内存空间足够与否,都会回收它的内存
虚引用:虚引用并不会决定对象的生命周期。如果一个对象仅持有虚引用,那么它就和没有任何引用一样,在任何时候都可能被垃圾回收器回收。

8. Hashcode的作用*

利用哈希算法,配合基于散列的集合一起正常运行,Java中的hashCode方法就是根据一定的规则将与对象相关的信息(比如对象的存储地址,对象的字段等)映射成一个数值,这个数值称作为散列值,降低equals的调用,实现存放的值不会重复。
Note:重写equals必须重写hashcode方法,equals相等,hashcode也必须相等。
一般对于存放到Set集合或者Map中键值对的元素,需要按需要重写hashCode与equals方法,以保证唯一性!
例如hashset存放多个对象,重写equals和hashcode
两个对象相等,其HashCode一定相同;
两个对象不相等,其HashCode有可能相同;
HashCode相同的两个对象,不一定相等;
HashCode不相同的两个对象,一定不相等;

9. HashMap的hashcode的作用*

https://blog.csdn.net/baidu_31657889/article/details/52298367
Java中的集合(Collection)有两类,一类是List,再有一类是Set。前者集合内的元素是有序的,元素可以重复;后者元素无序,但元素不可重复。 equals方法可用于保证元素不重复,但是,如果每增加一个元素就检查一次,如果集合中现在已经有1000个元素,那么第1001个元素加入集合时,就要调用1000次equals方法。这显然会大大降低效率。
HashMap的数据结构是 数组+链表形式存储数据,继承AbstractMap,实现Map接口,主要用于查找的快捷性。

10. 为什么重载hashCode方法?*

一般的地方不需要重载hashCode,只有当类需要放在HashTable、HashMap、HashSet等等hash结构的集合时才会重载hashCode,那么为什么要重载hashCode呢?就HashMap来说,好比HashMap就是一个大内存块,里面有很多小内存块,小内存块里面是一系列的对象,可以利用hashCode来查找小内存块hashCode%size(小内存块数量),所以当equal相等时,hashCode必须相等,而且如果是object对象,必须重载hashCode和equal方法。

11. ArrayList、LinkedList、Vector的区别*

ArrayList: 线程不安全,数组,适合查找,可自动扩容50%
三个构造器,无参,容量,Collection接口,transient Object[] elementData;不被序列化。
LinkedList:线程不安全,链表,审核插入,删除
Vector: 线程安全,数组,适合查找,可自动扩容100%

12. String、StringBuffer与StringBuilder的区别*

String 是final修饰的,字符串常量,String对象一旦创建之后该对象是不可更改的
StringBuffer 字符串变量,对象可变,线程安全,适合多线程下字符缓冲区大量操作
StringBuider 字符串变量,对象可变,线程不安全,适用单线程下载字符缓冲区进行大量操作的情况,都是继承AbstractStringBuilder super.容量为16

13. Map、Set、List、Queue、Stack的特点与用法。

Map map集合,k-v键值对存储
HashTable 和 HashMap 是 Map 的实现类
HashTable 是线程安全的,不能存储 null 值
HashMap 不是线程安全的,可以存储 null 值
TreeMap可以保证顺序,HashMap不保证顺序,即为无序的。
Set 集合,无序,不重复
List 数组集合,ArrayList , Vector , LinkedList 是 List 的实现类
ArrayList 是线程不安全的, Vector 是线程安全的,这两个类底层都是由数组实现的
LinkedList 是线程不安全的,底层是由链表实现的
Queue 队列,提供了几个基本方法,offer、poll、peek等。已知实现类有LinkedList、PriorityQueue等。
Stack 栈,继承自Vector,实现一个后进先出的栈。提供了几个基本方法,push、pop、peak、empty、search等。
HashMap和HashTable的区别
https://blog.csdn.net/yu849893679/article/details/81530298

14. JDK7与JDK8中HashMap的实现*

JDK8在JDK7的基础上引入了红黑树-b,因为链表过长,会导致效率很低,将原来链表数组的每一个链表分成奇偶两个子链表分别挂在新链表数组的散列位置,这样就减少了每个链表的长度,增加查找效率

15. HashMap和ConcurrentHashMap的区别,HashMap的底层源码*

HashMap是线程不安全的,ConcurrentHashMap是线程安全的,适用于高并发,ConcurrentHashMap就是一个分段的hashtable,根据自定的hashcode算法生成的对象来获取对应hashcode的分段块进行加锁,不用整体加锁,提高了效率。
https://blog.csdn.net/qpzkobe/article/details/78948197
HashMap的get(key)方法是获取key的hash值,计算hash&(n-1)得到在链表数组中的位置first=tab[hash&(n-1)],先判断first的key是否与参数key相等,不等就遍历后面的链表找到相同的key值返回对应的Value值即可。
HashMap的put(key)方法是判断键值对数组tab[]是否为空或位null,否则以默认大小resize();根据键值key计算hash值得到插入的数组索引i,如果tab[i]==null,直接新建节点添加,否则判断当前数组中处理hash冲突的方式为链表还是红黑树(check第一个节点类型即可),分别处理。
构造hash表时,如果不指明初始大小,默认大小为16(即Node数组大小16),如果Node[]数组中的元素达到(填充比*Node.length)重新调整HashMap大小 变为原来2倍大小,扩容很耗时

16. ConcurrentHashMap能完全替代HashTable吗?

Hash table虽然性能上不如ConcurrentHashMap,但并不能完全被取代,两者的迭代器的一致性不同的,ConcurrentHashMap由于分段锁,弱一致性主要是为了提升效率。
强一致性就如hashtable一样,锁整个map。

17. 为什么HashMap是线程不安全的*

在某一时刻同时操作HashMap并执行put操作,而有大于两个key的hash值相同,如图中a1、a2,这个时候需要解决碰撞冲突,而解决冲突的办法上面已经说过,对于链表的结构在这里不再赘述,暂且不讨论是从链表头部插入还是从尾部初入,这个时候两个线程如果恰好都取到了对应位置的头结点e1,而最终的结果可想而知,a1、a2两个数据中势必会有一个会丢失
当多个线程同时检测到总数量超过门限值的时候就会同时调用resize操作,各自生成新的数组并rehash后赋给该map底层的数组table,结果最终只有最后一个线程生成的新数组被赋给table变量,其他线程的均会丢失。而且当某些线程已经完成赋值而其他线程刚开始的时候,就会用已经被赋值的table作为原始数组,这样也会有问题。

18. 多并发情况下HashMap是否还会产生死循环*

https://blog.csdn.net/u010412719/article/details/52049347
不会,jdk1.8版本以后已经没有这个问题了,没有transfer这个函数了do while可能造成的死循环,对原有造成死锁的关键原因点(新table复制在头端添加元素)改进为依次在末端添加新的元素

19. TreeMap、HashMap、LindedHashMap的区别*

LinkedHashMap可以保证HashMap集合有序。存入的顺序和取出的顺序一致。
TreeMap实现SortMap接口,能够把它保存的记录根据键排序,默认是按键值的升序排序,也可以指定排序的比较器,当用Iterator 遍历TreeMap时,得到的记录是排过序的。
HashMap不保证顺序,即为无序的,具有很快的访问速度。HashMap最多只允许一条记录的键为Null;允许多条记录的值为 Null;HashMap不支持线程的同步。

20. Collection包结构,与Collections的区别

Collection是个java.util下的接口,它是各种集合结构的父接口。
Collections是个java.util下的类,它包含有各种有关集合操作的静态方法。

21. try?catch?finally,try里有return,finally还执行么

如果finally没有return 相同返回值变量,则返回try里面的return,否则finally 的return 值会影响 try里面return结果。
finally还是会执行的,除非中途遇到jvm退出。

22. Excption与Error包结构,OOM你遇到过哪些情况,SOF你遇到过哪些情况

都是Throwable的子类,Exception指出了合理的应用程序想要捕获的条件。Error 它用于指示合理的应用程序不应该试图捕获的严重问题,大多数这样的错误都是异常条件
Java Heap 溢出,虚拟机栈和本地方法栈溢出,运行时常量池溢出,方法区溢出
*Error 的定义:当应用程序递归太深而发生堆栈溢出时,抛出该错误。

23. Java(OOP)面向对象的三个特征与含义

封装:可见性封装,setget读写,将类的某些特征隐藏在类的内部,不允许外部程序直接访问,而是通过该类提供的方法来实现对隐藏信息的操作和访问。
继承:子类继承父类,可以得到父类的全部属性和方法(除了父类中的构造方法),java中的多继承可以通过接口来实现。
多态:一种是编译时多态,另外一种是运行时多态,编译时多态是通过方法的重载来实现的,运行时多态是通过方法的重写来实现的。

24. Override和Overload的含义去区别

重写,是子类覆盖父类方法,重新定义,但是,返回类型,参数,参数类型,抛出异常都和父类一致,被覆盖的方法不能private,子类函数访问权限要大于等于父类的,
子类无法覆盖父类的static方法或private方法。
重载,是一个类中,方法名同名,但是具有不同程度参数类型,不同的参数个数,不同的参数顺序。

25. Interface与abstract类的区别

1.抽象类可以有构造方法,接口中不能有构造方法。
2.抽象类中可以有普通成员变量,接口中没有普通成员变量
3.抽象类中可以包含非抽象的普通方法,接口中的所有方法必须都是抽象的,不能有非抽象的普通方法。
4. 抽象类中的抽象方法的访问类型可以是public,protected和(默认类型,虽然eclipse下不报错,但应该也不行),但接口中的抽象方法只能是public类型的,并且默认即为public abstract类型。
5. 抽象类中可以包含静态方法,接口中不能包含静态方法
6. 抽象类和接口中都可以包含静态成员变量,抽象类中的静态成员变量的访问类型可以任意,但接口中定义的变量只能是public static final类型,并且默认即为public static final类型。
7. 一个类可以实现多个接口,但只能继承一个抽象类。

26. Static?class?与non?static?class的区别

内部静态类不需要有指向外部类的引用。但非静态内部类需要持有对外部类的引用。
非静态内部类能够访问外部类的静态和非静态成员。静态类不能访问外部类的非静态成员。他只能访问外部类的静态成员。一个非静态内部类不能脱离外部类实体被创建,一个非静态内部类可以访问外部类的数据和方法,因为他就在外部类里面。java多态的实现原理。

27. foreach与正常for循环效率对比

对于数组来说,for和foreach循环效率差不多,但是对于链表来说,for循环效率明显比foreach低。

28. Java?IO与NIO*

NIO是为了弥补IO操作的不足而诞生的,NIO的一些新特性有:非阻塞I/O,选择器,缓冲以及管道。管道(Channel),缓冲(Buffer) ,选择器( Selector)是其主要特征
IO是面向流的,NIO是面向块(缓冲区)的。
IO是阻塞的,NIO是非阻塞的。
多连接,少数据可以用NIO
少连接,大数据可以用IO

29. java反射的作用与原理*

https://blog.csdn.net/sinat_38259539/article/details/71799078
JAVA反射机制是在运行状态中,对于任意一个类,都能够知道这个类的所有属性和方法;对于任意一个对象,都能够调用它的任意一个方法和属性;这种动态获取的信息以及动态调用对象的方法的功能称为java语言的反射机制。
在JAVA中,只有给定类的名字,就可以通过反射机制来获取类的所有信息,可以动态的创建对象和编译。
JAVA语言编译之后会生成一个.class文件,反射就是通过字节码文件找到某一个类、类中的方法以及属性等。

30. 泛型常用特点

泛型是具有占位符(类型参数)的类、结构、接口和方法,这些占位符是类、结构、接口和方法所存储或使用的一个或多个类型的占位符。
使用泛型类型可以最大限度地重用代码、保护类型的安全以及提高性能。
通过类型擦除来实现

31. 解析XML的几种方式的原理与特点:DOM、SAX

DOM分析器是把整个XML文档转化为DOM树放在内存中
SAX解析采用事件驱动,通过事件处理函数实现对xml文档的访问。

32. Java1.7与1.8,1.9,10 新特性

1.7
1.switch中可以使用字串了
2.运用List tempList = new ArrayList<>(); 即泛型实例化类型自动推断
3.语法上支持集合,而不一定是数组
4.新增一些取环境信息的工具方法
5.Boolean类型反转,空指针安全,参与位运算
6.两个char间的equals
7.安全的加减乘除
8.map集合支持并发请求,且可以写成 Map map = {name:“xxx”,age:18};

1.8

  1. 允许在接口中有默认方法实现
  2. Lambda表达式
  3. 函数式接口
  4. 方法和构造函数引用
  5. Lambda的范围
  6. 内置函数式接口
  7. Streams
  8. Parallel Streams
  9. Map
  10. 时间日期API
  11. Annotations

1.9

  1. Jigsaw 项目;模块化源码
  2. 简化进程API
  3. 轻量级 JSON API
  4. 钱和货币的API
  5. 改善锁争用机制
  6. 代码分段缓存
  7. 智能Java编译, 第二阶段
  8. HTTP 2.0客户端
  9. Kulla计划: Java的REPL实现

33. 设计模式:单例、工厂、适配器、责任链、观察者等等

单例:
public class Singleton1 {
public static final Singleton1 instance = new Singleton1();
private Singleton1(){
}
public static Singleton1 getInstance(){
return instance;
}

public class Singleton2 {
private static class SingletonHolder {
//静态初始化器,由JVM来保证线程安全
private static Singleton2 instance = new Singleton2();
}
private Singleton2() {
}
public static Singleton2 getInstance() {
return SingletonHolder.instance;
}

34. JNI的使用*

jni是一种协议,这个协议用来沟通java代码和外部的本地代码(c/c++),通过这个协议,java代码就可以调用外部的c++代码。
1、在java本地代码中声明一个native方法:例如:public native String helloJni();
2、在eclipse中创建一个文件夹,名称必须命名为jni;
3、在jni这个文件夹下创建一个.c文件,按照c代码的规范来写
4、ndk-build.cmd指令编译c代码(注意:如果不配置Android.mk文件的话就会报错);
5、配置Android.mk文件;
6、编译过后,自动生成一个.so的动态链接库;
7、在java代码中,把动态链接库加载到jvm虚拟机中加入一个静态代码块
8、像调用java代码一样,调用native方法;

35. AOP是什么*

面向切面编程,不影响功能的情况下添加内容扩展,比如添加log,权限等,通过Aspect切面,把业务共同调用的逻辑或者责任封装起来,减少重复代码,降低模块之间的耦合度。
1、横切关注点
对哪些方法进行拦截,拦截后怎么处理,这些关注点称之为横切关注点
2、切面(aspect)
类是对物体特征的抽象,切面就是对横切关注点的抽象
3、连接点(joinpoint)
被拦截到的点,因为Spring只支持方法类型的连接点,所以在Spring中连接点指的就是被拦截到的方法,实际上连接点还可以是字段或者构造器
4、切入点(pointcut)
对连接点进行拦截的定义
5、通知(advice)
所谓通知指的就是指拦截到连接点之后要执行的代码,通知分为前置、后置、异常、最终、环绕通知五类
6、目标对象
代理的目标对象
7、织入(weave)
将切面应用到目标对象并导致代理对象创建的过程
8、引入(introduction)
在不修改代码的前提下,引入可以在运行期为类动态地添加一些方法或字段

36. OOP是什么

面向对象编程,一种编程思想,万物皆对象

37. AOP与OOP的区别*

AOP: (Aspect Oriented Programming) 面向切面编程。是目前软件开发中的一个热点,也是Spring框架中容。利用AOP可以对业务逻辑的各个部分进行隔离,从而使得业务逻辑各部分之间的耦合度降低,提高程序的可重用性,同时提高了开发的效率。主要的功能是:日志记录,性能统计,安全控制,事务处理,异常处理等等。
AOP、OOP在字面上虽然非常类似,但却是面向不同领域的两种设计思想。OOP(面向对象编程)针对业务处理过程的实体及其属性和行为进行抽象封装,以获得更加清晰高效的逻辑单元划分。 而AOP则是针对业务处理过程中的切面进行提取,它所面对的是处理过程中的某个步骤或阶段,以获得逻辑过程中各部分之间低耦合性的隔离效果。这两种设计思想在目标上有着本质的差异。