【面试题系列】——Java基础

简介: 本文主要包括Java基础及面向对象相关面试题。

本文主要包括Java基础及面向对象相关面试题。

1,Java科普

1.1 为什么安装包要分JDK和JRE?

JRE主要包含JVM,用于运行Java程序。
JDK包含了JRE,除此之外,包含了比如像javac等程序开发需要用到的工具。

先来说说什么是JDK,JRE。

JDK:Java Development Kit Java开发工具包【开发Java程序用】

JRE:Java Runtiome Environment Java运行环境【运行Java程序用】

【注:下载的JDK包是包含了JDK和JRE的,JDK和JRE是逻辑上的区分,两者在JDK下载的包中都有】

JDK与JRE的关系:以Java代码运行为例,编写好Java代码之后,通过javac将java源文件编译成class字节码文件,然后通过java命令,运行字节码文件。那么运行字节码的环境就是JRE。(JRE的核心就是JVM)

了解完JDK和JRE是什么之后,再聊聊为什么开发者当时要把一个安装包分成两部分呢?

平常使用的软件都是一键安装的,但JDK需要安装两次。JDK的发明者不会这么无聊,故意给开发者增加麻烦。

【我想】:这应该跟生产环境的部署问题有关,关于生产环境部署JDK还是JRE一直饱受争议,具体情况根据项目而定。

出于对性能的考虑,尽可能的使服务器轻,能少装一个软件就少装一个,这样生产环境部署JRE就OK了。【又省了资源】

除了这个方面之外,还有一种可能。JDK的开发也有可能是分团队的,JDK和JRE可能是交由不同团队开发,JDK和JRE的耦合也可能因此而减小,从而加快JDK的迭代版本。(毕竟现在JDK一年更新两次)

1.2 为什么Java语言是跨平台的?

JVM有两个功能
- 将class字节码转换为机器码
- 兼容不同的操作系统

跨平台和Java 虚拟机有关。

JVM有两个主要的功能:

  • 适配不同的操作系统的指令集(兼容不同的操作系统)
  • 翻译字节码文件为机器码执行

(Oracle官网上下载JDK,不同操作系统的JDK是不一样的,对应不同的虚拟机)

1.3 为什么安装完JDK后要设置环境变量?

在解决这个问题之前,先来了解一些环境变量是干嘛的:

环境变量是在操作系统中一个具有特定名字的对象,它包含了一个或者多个应用程序所将使用到的信息。例如Windows和DOS操作系统中的path环境变量,当要求系统运行一个程序而没有告诉它程序所在的完整路径时,系统除了在当前目录下面寻找此程序外,还应到path中指定的路径去找。用户通过设置环境变量,来更好的运行进程。

简单来说,运行一个程序(命令),操作系统会从当前目录寻找,或者从环境变量中寻找。

换句话说,如果在java,javac的目录下执行这个两个命令,是没有问题的。但是如果更换了目录,系统在当前目录找不到,就会去环境变量中寻找。所以设置环境变量的根本目的是在电脑的任何一个文件夹下都可以编译运行Java程序。

1.4 Java和C++区别

题外话,Java和C++有什么区别?(据说有些面试官老爱干这种事)

  • C++支持多继承,Java支持单继承
  • Java有垃圾回收机制
  • Java不支持指针,更加安全

2,数据类型&变量

2.1 boolean占几个字节?

表示变量:4个字节(转换为int存储)
表示byte数组:1个字节

2.2 为什么long可以自动转换为float?

float,double采用指数方式存储,能表示的数比long更大
System.out.println(Long.MAX_VALUE);
System.out.println(Float.MAX_VALUE);
System.out.println(Double.MAX_VALUE);
        System.out.println(Float.MAX_VALUE>Long.MAX_VALUE);


9223372036854775807
3.4028235E38
1.7976931348623157E308
true

float和double使用指数表示,取值范围在

-3.4*10^38 - 3.4*10^38

顺便看看float和double的精度:7位和16位。

2.3 包装类型和基本数据类型的区别

初始值:包装类型的初始值为null,基本数据类型的初始值基本上是0,char是'u000'
存储方式:包装类型存在堆里,基本数据类型存在栈中

2.4 String,StringBuffer,StringBuilder的区别

- 可变性
String底层使用fina修饰的数组实现,是不可变的,StringBuffer和StringBuilder是可变的
- 安全性
String不可变,自然线程安全,StringBuffer使用synchronized同步锁实现线程安全,StringBuilder是线程不安全的
  • 可变性

String是不可变的,StringBuffer和StringBuilder是可变的

        String string1 = "111";
        string1 = "222";
        System.out.println(string1);
        
        string1指向222时,创建了一个新的对象并指向它

String 底层使用final修饰的数组实现,故是不变的

public final class String implements java.io.Serializable, Comparable<String>, CharSequence {
   
    private final char value[];
  • 安全性

StringBuffer和String是线程安全的,,StringBuilder是线程不安全的。

String 中的对象是不可变的,也就可以理解为常量,线程安全。

StringBuffer 对方法加了synchronized同步锁所以是线程安全的。

  • 对于三者使用的总结

    1. 操作少量的数据: 适用String
    2. 单线程操作字符串缓冲区下操作大量数据: 适用StringBuilder
    3. 多线程操作字符串缓冲区下操作大量数据: 适用StringBuffer

2.5 String s = "Hello";s = s + "world!";这两行代码执行后,原始的String对象中的内容到底变了没有?

没有,只是指向了另外一个对象。

因为String被设计成不可变(immutable)类(final修饰),所以它的所有对象都是不可变对象。

在这段代码中,s原先指向一个String对象,内容是 "Hello",然后对s进行了+操作

这时,s不指向原来那个对象了,而指向了另一个 String对象,内容为"Hello world!"

原来那个对象还存在于内存之中,只是s这个引用变量不再指向它了。

2.6 String str =“i”;和 String str = new String("i");有区别吗?

前者会被JVM分配到常量池中,常量池中没有重复的元素,如果再次创建一个字符串变量等于i的话,就会直接指向常量池中的i。

后者是new了一个对象,堆中是允许对象重复的。

前者会被JVM分配到常量池中,常量池中没有重复的元素。

String str1 =“i”;
String str2 =“i”;

str2不会重新创建一个常量,而是指向str1。

String str1 = new String("i");
String str2 = new String("i");

str1会在堆内存中创建对象

str2还是会再次创建一个新的对象

2.7 如何将字符串反转?

使用StringBuilder或者StringBuffer的reverse()方法。

        StringBuffer str1 = new StringBuffer("12345");
        StringBuffer str2 = str1.reverse();
        System.out.println(str2);
        
        54321

2.8 Java有几种变量?

  • 类变量

独立于方法之外,必须用static修饰

  • 实例变量

独立于方法之外,不用static修饰

  • 局部变量

方法中的变量

2.9 引用数据类型包含哪几种?

  • 接口
  • 数组

3,运算符

3.1 ==和equals的区别

equals用于比较内容是否相同(源自Object类,通常被重写)

==对于基本数据类型比较值相同,对于引用数据类型比较内存地址是否相同(是否是同一个对象)

知乎上非常形象的一张图:

img

3.2 &和&&区别(|和||同理)

& : 两边都为true时才为true

|:两边有一个为false即为false

短路逻辑运算符

&&:左边为fasle直接返回flase(不计算右边)

||:左边为true直接返回true(不计算右边)

就是为了简化计算量

^表示异或,相同为false,不同为true

4,面向对象

4.1 什么是面向对象?

如果摒弃软件开发的范畴,这是一种通过明确社会分工而提高效率的方法。

在软件开发的范围内,就是通过抽象出系统功能而实现最大化代码复用的开发模式。

4.2 封装相关

  • 什么是封装

通过隐藏实现,暴露接口,一来实现代码解耦,二来通过访问修饰符保证数据安全。

4.3 继承相关

  • 继承的作用?

实现代码复用

  • 继承的规则?

    • 子类继承父类非private的属性和方法
    • 子类可以扩展自己的属性和方法
  • 构造器是否会被继承?

    • 构造器不会被继承,但子类对象初始化时会调用父类无参构造器

    【为什么。子类和父类有最基本的依赖关系,比如说数据依赖】

    • 当父类显式写了有参构造器,且没有无参构造器。子类继承父类的时候必须显式的调用父类的有参构造器。调用的方式可以使用super(a,b)来调用。
  • 子类父类的初始化顺序

    原则:静态优于非静态,父类优于子类
    
    - 父类静态变量,静态语句块
    - 子类静态变量,静态语句块
    
    - 父类非静态代码块,构造器
    - 子类非静态代码块,构造器

4.4 多态相关

  • 什么是多态?

一类事物的多种表现形态。(比如手机有各种各样的品牌,但都属于手机这一类事物)

  • 如何体现多态?

方法重载:针对本类的不同方法而言,方法名相同,参数不同(个数,顺序)【返回类型随意】

方法重写:针对继承而言,除了方法体可以自定义外,其他必须与父类保持一致(方法名,返回类型,参数)

  • 向上转型&向下转型

up:子类转换为父类,目的是访问父类的公共方法,实现代码的复用和简洁(比如100个类把公共方法写在父类中,就不需要每个类都写一遍了)

down:父类转换为子类,据说是为了调用子类的扩展方法。(为啥不直接new一个对象,已提交知乎问答)

4.5 关键词static

  • 修饰变量

称为静态变量,类变量,全局变量

可直接通过类名.变量名访问

  • 修饰方法

称为静态方法,类方法

可通过类名.方法名直接访问

  • 非static方法可以访问static方法,static方法不能访问非static方法

4.6 关键词final

  • 修饰类不能被继承
  • 修饰方法不能被重写
  • 修饰变量则变量变为常量

4.7 接口和抽象类的区别?

  • 继承与实现

类只能单继承,但可以实现多接口

  • 方法是否能实现

抽象类不仅可以做方法声明,也可以做方法实现。(接口只能做方法声明)

  • 修饰符

接口的变量都默认采用final修饰,方法采用public修饰。

抽象类可自定义。

4.8 为什么重写equals必须重写hashCode?

equals和hashCode位于Object类中,所有的类都会继承Object类。

equals通常被用来比较对象的内容是否相同,hashCode是用来返回对象Hash值的一种方法。

如果不重写hashCode会导致,equals相同但hashCode不相同,equals不相同但hashCode相同。

重写的目的一来为了避免hash冲突,二来提高对象访问速度。

目录
相关文章
|
4月前
|
存储 Java
【IO面试题 四】、介绍一下Java的序列化与反序列化
Java的序列化与反序列化允许对象通过实现Serializable接口转换成字节序列并存储或传输,之后可以通过ObjectInputStream和ObjectOutputStream的方法将这些字节序列恢复成对象。
|
1月前
|
存储 缓存 算法
面试官:单核 CPU 支持 Java 多线程吗?为什么?被问懵了!
本文介绍了多线程环境下的几个关键概念,包括时间片、超线程、上下文切换及其影响因素,以及线程调度的两种方式——抢占式调度和协同式调度。文章还讨论了减少上下文切换次数以提高多线程程序效率的方法,如无锁并发编程、使用CAS算法等,并提出了合理的线程数量配置策略,以平衡CPU利用率和线程切换开销。
面试官:单核 CPU 支持 Java 多线程吗?为什么?被问懵了!
|
1月前
|
存储 算法 Java
大厂面试高频:什么是自旋锁?Java 实现自旋锁的原理?
本文详解自旋锁的概念、优缺点、使用场景及Java实现。关注【mikechen的互联网架构】,10年+BAT架构经验倾囊相授。
大厂面试高频:什么是自旋锁?Java 实现自旋锁的原理?
|
1月前
|
存储 缓存 Java
大厂面试必看!Java基本数据类型和包装类的那些坑
本文介绍了Java中的基本数据类型和包装类,包括整数类型、浮点数类型、字符类型和布尔类型。详细讲解了每种类型的特性和应用场景,并探讨了包装类的引入原因、装箱与拆箱机制以及缓存机制。最后总结了面试中常见的相关考点,帮助读者更好地理解和应对面试中的问题。
74 4
|
2月前
|
存储 缓存 Java
java基础:IO流 理论与代码示例(详解、idea设置统一utf-8编码问题)
这篇文章详细介绍了Java中的IO流,包括字符与字节的概念、编码格式、File类的使用、IO流的分类和原理,以及通过代码示例展示了各种流的应用,如节点流、处理流、缓存流、转换流、对象流和随机访问文件流。同时,还探讨了IDEA中设置项目编码格式的方法,以及如何处理序列化和反序列化问题。
92 1
java基础:IO流 理论与代码示例(详解、idea设置统一utf-8编码问题)
|
2月前
|
算法 Java 数据中心
探讨面试常见问题雪花算法、时钟回拨问题,java中优雅的实现方式
【10月更文挑战第2天】在大数据量系统中,分布式ID生成是一个关键问题。为了保证在分布式环境下生成的ID唯一、有序且高效,业界提出了多种解决方案,其中雪花算法(Snowflake Algorithm)是一种广泛应用的分布式ID生成算法。本文将详细介绍雪花算法的原理、实现及其处理时钟回拨问题的方法,并提供Java代码示例。
96 2
|
3月前
|
安全 Java API
【Java面试题汇总】Java基础篇——String+集合+泛型+IO+异常+反射(2023版)
String常量池、String、StringBuffer、Stringbuilder有什么区别、List与Set的区别、ArrayList和LinkedList的区别、HashMap底层原理、ConcurrentHashMap、HashMap和Hashtable的区别、泛型擦除、ABA问题、IO多路复用、BIO、NIO、O、异常处理机制、反射
|
2月前
|
JSON 安全 前端开发
第二次面试总结 - 宏汉科技 - Java后端开发
本文是作者对宏汉科技Java后端开发岗位的第二次面试总结,面试结果不理想,主要原因是Java基础知识掌握不牢固,文章详细列出了面试中被问到的技术问题及答案,包括字符串相关函数、抽象类与接口的区别、Java创建线程池的方式、回调函数、函数式接口、反射以及Java中的集合等。
38 0
|
4月前
|
XML 存储 JSON
【IO面试题 六】、 除了Java自带的序列化之外,你还了解哪些序列化工具?
除了Java自带的序列化,常见的序列化工具还包括JSON(如jackson、gson、fastjson)、Protobuf、Thrift和Avro,各具特点,适用于不同的应用场景和性能需求。
|
4月前
|
Java
【Java基础面试三十七】、说一说Java的异常机制
这篇文章介绍了Java异常机制的三个主要方面:异常处理(使用try、catch、finally语句)、抛出异常(使用throw和throws关键字)、以及异常跟踪栈(异常传播和程序终止时的栈信息输出)。

热门文章

最新文章