Java教程

java基础面试题?

本文主要是介绍java基础面试题?,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!

面试题?

  • 1.==和equals的区别
  • 2.jdk和jre的区别
  • 3.两个对象的 hashCode()相同,则 equals()也一定为 true,对吗?
  • 4.final在java中的作用?
  • 5.重写和重载的区别
  • 6.java中的Math.round(-1.5)等于多少?
  • 7.String属于基础数据类型吗?
  • 8.Java中八大基本类型数据
  • 9.java中操作字符串都有哪些类?(String、StringBuffer、StringBuilder)它们之间有什么区别?
  • 10.String str="i"与 String str=new String(“i”)一样吗?
  • 11.如何将字符串反转?
  • 11.String类常用的方法都有那些?
  • 12.抽象类必须要有抽象方法吗?
  • 13.普通类和抽象类有哪些区别?
  • 14.抽象类能使用 final 修饰吗?
  • 15.接口和抽象类有什么区别?
  • 16、java中IO流分为几种?
  • 17.BIO、NIO、AIO 有什么区别?

1.==和equals的区别

在这里插入图片描述
在这里插入图片描述
==比较:
实际上比较的是地址值,因为在编译String s1="song"的时候,其实在jvm常量池中创建了一个内容为song的地址值,然后让s1去指向song,而不是把song直接赋值给s1
在这里插入图片描述
然后在执行String s2=new String(“song”)的视乎,要记住每new一次就会出现一个新的对象。所以这种情况是直接在堆内存中开辟了新的空间,存储的是在常量池中的song,所以堆内存中其实也是存储的是song的地址
在这里插入图片描述
==指的是引用的地址值是否相同,equals指的是引用的值是否相同,如果对象中没有重写equals方法,那么他们的也是比较的是引用的地址值是否相同。

2.jdk和jre的区别

  • jre(java运行时环境) :提供java运行环境
    jre=jvm+运行类库
  • jdk(java开发工具包):提供java程序的运行环境和开发环境
    jdk=jre+kit(开发工具包)
    .java文件(源文件) 编译时期(在检测语法问题)
    .class文件 (字节码对象) 运行时期(检测java程序的逻辑问题)

3.两个对象的 hashCode()相同,则 equals()也一定为 true,对吗?

两个对象的hashCode()相同,equals()不一定为true;两个对象的equals为true,则两个对象的hashcode一定为true;

hashCode的存在主要是用于查找的快捷,比如我们常用的HashMap等集合,hashCode用来在散列的存储结构中确定对象的存储地址。

java中所有的对象都有一个父类Object,而Object有一个hashCode方法,Java的所有类都有hashcode方法。
我们来看看hashcode的计算方法:

for (Object element : a)
    result = 31 * result + (element == null ? 0 : element.hashCode());

hashcode其实就是对一个对象中的每个元素进行一次运算生成的结果值,两个不同的对象是有可能出现同一个hash值。
比如:

String s1="Ma";
String s2="NB";
System.out.println(s1.hashCode()==s2.hashCode());  //true
System.out.println(s1.equals(s2));  //false

虽然两个Ma和NB两个字符串不同,但是他们有相同的hashcode值2484。

创建实体类的时候如果要使用hashCode方法或equals方法时需要在实体类中重写:

@Override
public boolean equals(Object o) {
    if (this == o) return true;
    if (o == null || getClass() != o.getClass()) return false;
    User user = (User) o;
    return Objects.equals(name, user.name) &&
            Objects.equals(age, user.age);
}

@Override
public int hashCode() {
    return Objects.hash(name, age);
}

同理,实体对象同样存在两个不同对象存在同一个hash值的情况。

4.final在java中的作用?

在java中final中可以修饰类、变量、方法

  1. 修饰类时:
    当用final修饰一个类时,表明这个类不能被继承。也就是最终类。final类中的成员变量可以根据需要设为final,但是要注意final类中的所有成员方法都会被隐式的指定为final方法。
  2. Final修饰方法:
    当final修饰的方法后该方法不能被子类重写(可以重载多个final修饰的方法), 注意:重写的前提是子类可以从父类中继承此方法,如果父类中用final修饰的方法同时访问修饰符是private时,子类中则可以定义相同的方法名和参数
  3. final修饰变量
    final在修饰基本数据类型变量时,该变量赋值后,则不允许改变,如果修饰的引用数据类型时,则代表着引用的地址值不能改变,但是地址值所指向的内容时可以改变的。

①修饰成员变量时:修饰成员变量时必须显示初始化,初始化方式有两种,第一就是变量声名时直接初始化,二就是变量声明后不初始化,但必须要在这个变量所在的类的所有构造函数中对这个变量进行赋值。
②修饰局部变量时:当函数的参数通过final进行定义时,代表着该参数为只读,可以读取使用该参数,但不能修改该参数值。

5.重写和重载的区别

  1. Override 特点
    从字面上看,重写就是 重新写一遍的意思。其实就是在子类中把父类本身有的方法重新写一遍。子类继承了父类原有的方法,但有时子类并不想原封不动的继承父类中的某个方法,所以在方法名,参数列表,返回类型(除过子类中方法的返回值是父类中方法返回值的子类时)都相同的情况下, 对方法体进行修改或重写,这就是重写。但要注意子类函数的访问修饰权限不能少于父类的。

    • 发生在父类与子类之间
    • 方法名,参数列表,返回类型(除过子类中方法的返回类型是父类中返回类型的子类)必须相同
    • 访问修饰符的限制一定要大于被重写方法的访问修饰符(public>protected>default>private)
    • 重写方法一定不能抛出新的检查异常或者比被重写方法申明更加宽泛的检查型异常
  2. Overload 特点

    • 重载Overloading是一个类中多态性的一种表现。
    • 在一个类中,同名的方法如果有不同的参数列表(参数类型不同、参数个数不同甚至是参数顺序不同)则视为重载。同时,重载对返回类型没有要求,可以相同也可以不同,但不能通过返回类型是否相同来判断重载。
    • 重载Overload是一个类中多态性的一种表现
    • 重载要求同名方法的参数列表不同(参数类型,参数个数甚至是参数顺序)
    • 重载的时候,返回值类型可以相同也可以不相同。无法以返回型类型作为重载函数的区分标准
      面试问:

答:方法的重载和重写都是实现多态的方式,区别在于前者实现的是编译时的多态性,而后者实现的是运行时的多态性。重载发生在一个类中,同名的方法如果有不同的参数列表(参数类型不同、参数个数不同或者二者都不同)则视为重载;重写发生在子类与父类之间,重写要求子类被重写方法与父类被重写方法有相同的参数列表,有兼容的返回类型,比父类被重写方法更好访问,不能比父类被重写方法声明更多的异常(里氏代换原则)。重载对返回类型没有特殊的要求,不能根据返回类型进行区分。

6.java中的Math.round(-1.5)等于多少?

math的round方法是四舍五入,如果参数是负数,则往大的数如-1.5等于-1。

7.String属于基础数据类型吗?

引用数据类型,String并不是基本数据类,而是一个类class,是c++,java等语言编程中的字符串

8.Java中八大基本类型数据

1、字符类型: char 2、基本整型:byte,short,int,long 3、浮点型:float,double 4 布尔类型:boolean

9.java中操作字符串都有哪些类?(String、StringBuffer、StringBuilder)它们之间有什么区别?

String : final修饰,String类的方法都是返回new String。即对String对象的任何改变都不影响到原对象,对字符串的修改操作都会生成新的对象。

  • StringBuffer : 对字符串的操作的方法都加了synchronized,保证线程安全。
  • StringBuilder : 不保证线程安全,在方法体内需要进行字符串的修改操作,可以new StringBuilder对象,调用 StringBuilder对象的append、replace、delete等方法修改字符串。
    (1)String是不可变字符串 StringBuffer、StringBuilder是可变字符串。三者的底层都是以char[]形式保存字符串
    String底层初始化时默认char[]数组长度为0,StringBuffer、StringBuilder初始化默认的char[]数组长度为16
    (因为String不可变,每次对String进行操作都会生成新的字符窜)
    (2)StringBuffer中大部分的方法都是被synchronized关键字这就代表着StringBuffer是线程安全的。StringBuilder
    中的方法则没有,代表着他是一个线程不安全的。所以在单线程的情况下选择StringBuilder要更快,然而在多线程当中
    考虑使用StringBuffer更加安全些
    (3)在声明变量的时候如果根据情况这个变量声明之后基本上不做修改我自己考虑直接使用String,不同new String()的
    方式进行声明那样就不会再堆内存中创建对象,此时String变量直接指向常量池,并且可以复用,效率更高
public StringBuffer() {
        super(16);
}

10.String str="i"与 String str=new String(“i”)一样吗?

String str = “i”代表着声明了一个变量str,此时在常量池中创建了一个内容为i的字符串对象。
String str = new String(“I”);此时代表着创建了两个对象,str引用地址指向堆内存,如果常量池中没有字符窜i,则会
在常量池中创建第二个对象字符串i。

11.如何将字符串反转?

  1. 利用 StringBuffer 或 StringBuilder 的 reverse 成员方法:
public static String reverse(String str) {
	return new StringBuilder(str).reverse().toString();
}
  1. 利用 String 的 toCharArray 方法先将字符串转化为 char 类型数组,然后将各个字符进行重新拼接:
//自定义方法
public static String reverse(String str){
    char[] chars = str.toCharArray();
    //创建StringBuilder对象进行拼接
    StringBuilder builder = new StringBuilder();
    for (int i = chars.length - 1; i >= 0; i--) {
        builder.append(chars[i]);
    }
    return builder.toString();
}
  1. 利用 String 的 CharAt 方法取出字符串中的各个字符:
public static String reverse1(String str){
    //创建StringBuilder对象进行拼接
    StringBuilder builder = new StringBuilder();
    //获取字符窜长度
    int length = str.length();
    for (int i = length-1; i >=0; i--) {
        builder.append(str.charAt(i));
    }
    return builder.toString();
}
  1. 使用递归的方式进行反转
public static String reverse2(String str){
    //获取字符窜长度
    int length = str.length();
    if(length<=1){
        return str;
    }
    String left = str.substring(0, length/2);
    String right = str.substring(length/2,length);
    return reverse2(right)+reverse2(left);
}

11.String类常用的方法都有那些?

  • indexOf(String str):查找指定的字符在当前字符窜第一次出现的索引值
  • charAt(int index) 返回指定索引处得字符
  • replace(char oldChar,char newChar): 它是通过用 newChar 替换此字符串中出现的所有 oldChar
  • trim() 去除字符串两端的空白
  • split() 分割字符串 返回分割后的字符串数组
  • getBytes() 返回字符串的byte类型数组
  • length() 返回字符串的长度
  • toLowerCase() 字符串转小写
  • toUpperCase() 字符串转大写
  • substring() 截取字符串
  • equals() 字符串比较
1.最普通的用法
		String str1 = "aa,bb";
		String[] split1 = str1.split(",");
		System.out.println(split1.length);
		//这个结果是2,都知道的
2.比较普通的用法
		String str2 = "";
		String[] split2 = str2.split(",");
		System.out.println(split2.length);
		//这个结果是1,但部分人会认为这个的结果是0,
		//这个为什么是1,我会在后面说
3.看起来比较奇怪的用法
		String str3 = ",";
		String[] split3 = str3.split(",");
		System.out.println(split3.length);
		//这个结果是0,但部分人会认为结果是1,部分人会认为结果是2.
		//这个又为什么是0,我也会在后面说

12.抽象类必须要有抽象方法吗?

抽象类可以没有抽象方法,但是如果你的一个类已经声明成了抽象类,即使这个类中没有抽象方法,它也不能再实例化,即不能直接构造一个该类的对象。 如果一个类中有了一个抽象方法,那么这个类必须声明为抽象类,否则编译通不过。

13.普通类和抽象类有哪些区别?

抽象类不能被实例化
抽象类可以有抽象方法,抽象方法只需申明,无需实现
含有抽象方法的类必须申明为抽象类
抽象类的子类必须实现抽象类中所有抽象方法,否则这个子类也是抽象类
抽象方法不能被声明为静态 :抽象方法是没有方法体的,也就是不具体实现什么,如果是静态的意味着可以直接调用,然而这样是没有什么意义的。
抽象方法不能用 private 修饰
抽象方法不能用 final 修饰

14.抽象类能使用 final 修饰吗?

不能,抽象类是被用于继承的,final修饰代表不可修改、不可继承的。

15.接口和抽象类有什么区别?

1、抽象类和接口都不能直接实例化,如果要实例化,抽象类变量必须指向实现所有抽象方法的子类对象,接口变量必须指向实现所有接口方法的类对象。
2、抽象类要被子类继承,接口要被类实现。
3、接口只能做方法申明,抽象类中可以做方法申明,也可以做方法实现
4、接口里定义的变量只能是公共的静态的常量,抽象类中的变量是普通变量。:接口只是对一类事物的属性和行为更高层次的抽象。对修改关闭,对扩展(不同的实现implements)开放,接口是对开闭原则的一种体现。静态常量是不可以改变的,所以在接口中要是想要定义变量必须是静态常量
5、抽象类里的抽象方法必须全部被子类所实现,如果子类不能全部实现父类抽象方法,那么该子类只能是抽象类。同样,一个实现接口的时候,如不能全部实现接口方法,那么该类也只能为抽象类。
6、抽象方法只能申明,不能实现,接口是设计的结果 ,抽象类是重构的结果
7、抽象类里可以没有抽象方法
8、如果一个类里有抽象方法,那么这个类只能是抽象类
9、抽象方法要被实现,所以不能是静态的,也不能是私有的。
10、接口可继承接口,并可多继承接口,但类只能单继承。
接口和抽象的区别

  • 抽象类支持单继承,接口支持多继承,接口和实现类支持多实现
  • 抽象类可以定义构造方法,接口不能定义构造方法
  • 接口中的属性默认被public static final共同修饰,抽象方法默认被public abstact共同修饰
  • 接口的目的是为了给实现类注入更多的功能,抽象类是为了延展类的继承结构

16、java中IO流分为几种?

Java中的流分为两种,一种是字节流,另一种是字符流,分别由四个抽象类来表示(每种流包括输入和输出两种所以一共四个):InputStream,OutputStream,Reader,Writer。Java中其他多种多样变化的流均是由它们派生出来的。

17.BIO、NIO、AIO 有什么区别?

BIO是一个连接一个线程。 NIO是一个请求一个线程。 AIO是一个有效请求一个线程。
BIO:同步并阻塞,服务器实现模式为一个连接一个线程,即客户端有连接请求时服务器端就需要启动一个线程进行处理,如果这个连接不做任何事情会造成不必要的线程开销,当然可以通过线程池机制改善。
NIO:同步非阻塞,服务器实现模式为一个请求一个线程,即客户端发送的连接请求都会注册到多路复用器上,多路复用器轮询到连接有I/O请求时才启动一个线程进行处理。
AIO:异步非阻塞,服务器实现模式为一个有效请求一个线程,客户端的I/O请求都是由OS先完成了再通知服务器应用去启动线程进行处理。

这篇关于java基础面试题?的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!