Java 基础(一)

<注> Hello~ 此篇博客需要一丢丢的Java基础,更适合找工作的中国宝宝观看噢。如有错误,欢迎在评论区指出~

目录

1、JVM、JRE、JDK之间的关系

2、Java语言的特点

3、public、protected、default、private的区别

4、final、finally、finalize的区别

5、static关键字的作用

6、面向对象、面向过程的区别

7、继承、封装、多态

8、实现多态的三个必要条件

9、重写和重载的区别


1、JVM、JRE、JDK之间的关系

a) JVM ( Java Virtual Machine ) : Java虚拟机的缩写,它是Java程序运行的环境。JVM负责将Java源代码编译成字节码,并在运行时加载和执行字节码。

b) JRE(Java Runtime Environment):Java运行时环境的缩写,包含了JVM和运行Java程序所需的核心类库等组件。

c) JDK( Java Development Kit):Java开发工具包的缩写,它是Java开发人员用来开发Java程序的工具集合。JDK包含了JRE以及编译器、调试器、文档生成器等开发工具,开发人员使用JDK来编写、编译和调试Java程序。

因此,JDK包含了JRE和其他开发工具,JRE包含了JVM和运行Java程序所需的类库,而JVM是Java程序运行的环境。它们之间的关系是JDK包含了JRE,JRE包含了JVM。

 Java语言的编译过程中,源代码会首先被编译成字节码文件,然后再由Java虚拟机(JVM)将字节码文件转换成机器码执行。具体的转换过程如下:

(1)Java源代码编译:Java源代码通过Java编译器(javac)编译成字节码文件(.class文件)。

(2)类加载:当Java程序运行时,JVM会加载字节码文件,并将其解析成内存中的类结构。在加载过程中,JVM会检查字节码文件的格式是否正确,以及是否包含有错误的指令等。

(3)字节码解释执行:JVM会将字节码文件中的指令,逐条解释(也叫翻译)成机器码并执行,这种方式称为解释执行。

(4)  字节码编译执行:为了提高性能,JVM还可以将字节码文件中的热点代码(频繁执行的代码)编译成本地机器码,这种方式称为即时编译( Just-In-Time Compilation, JIT )。编译后的机器码可以直接在本地平台上执行,从而提高程序的执行效率。

通过这些步骤,Java程序可以在不同的平台上执行,并且可以通过JIT编译提高程序的性能。

 解释和编译都是将源代码转换为可执行代码的过程,但它们之间有一些重要的区别。

(1)解释是直接将源代码逐行翻译成机器代码并立即执行。解释器读取源代码的一行,将其翻译成机器代码,然后执行该指令,然后继续下一行。这种方式使得程序可以逐行执行,但也意味着在每次执行时都需要重新翻译源代码,因此解释器的执行速度通常比编译器慢。

(2)编译是将整个源代码文件一次性翻译成机器代码,生成一个可执行文件,然后再执行该文件。编译器会对源代码进行多次扫描和优化,以提高程序的性能和效率。编译生成的可执行文件可以在多次执行时重复使用,不需要每次都重新翻译源代码,因此编译后的程序通常比解释器执行速度更快。

为了便于理解,这里列出了源代码、字节码、机器码的具体概念。

(1)源代码:程序员编写的高级语言代码,通常是人们可读的形式,如C++、Java、Python等。源代码经过编译器或解释器的处理,会转化为字节码或机器码。

(2)字节码:一种中间代码,通常是在编译器或解释器中生成的,它不是针对特定硬件平台的机器码,而是针对虚拟机的代码。字节码执行的过程是一种解释执行的过程,相比直接执行机器码,速度会慢一些,但具有更好的跨平台性。

(3)机器码:计算机能够直接执行的二进制代码,它是由硬件平台所支持的特定指令集组成的。当源代码或字节码被编译成机器码后,计算机就能够直接执行这些指令,完成相应的操作。

2、Java语言的特点

(1)简单易学:Java语法与C++类似,但去掉了C++中难以理解的操作符重载多继承自动的强制类型转换指针内存管理等概念,不用手动管理对象的生命周期,使得它更易学易用。

(2)面向对象:Java是一种面向对象的编程语言,支持封装、继承和多态等面向对象的特性,可以不用严格按照顺序来执行每个动作。Java 语言全面支持动态绑定,而 C++语言只对虚函数使用动态绑定。

  动态绑定是指在程序运行时根据对象的实际类型确定调用哪个方法的过程。在面向对象编程中,一个对象可以引用不同的类型,而动态绑定允许调用相同的方法名时,根据对象的实际类型来确定调用的方法实现。

(3)具有平台独立性和可移植性:Java程序可以在不同的操作系统上运行,只需要安装对应的Java虚拟机即可。

(4)静态语言:在编译期间就能知道数据类型,在运行时就能检查类型的正确性,一旦确定类型后就不能再改,静态语言的执行效率要比动态语言高,速度更快。

(5)多线程支持:Java提供了多线程的支持,可以方便地实现并发编程,提高程序的性能。

(6)安全性:Java提供了安全性机制,如类加载器、字节码校验器等,可以防止恶意代码的执行。

(7) 健壮性(系统或设备在面对各种异常或恶劣条件下依然能够正常工作的能力):Java具有强类型机制、异常处理和垃圾的自动收集的功能。

(8)具有强大的标准库:Java提供了丰富的标准库,包括各种API和工具,可以帮助开发者快速开发应用程序。

(9)开源:Java是开源的,有一个庞大的社区支持,可以获得大量的开源库和工具。

(10)分布式:Java 语言支持 Internet 应用的开发,在基本的 Java 应用编程接口中有一个网络应用编程接口(java net),它提供了用于网络应用编程的类库,包括 URL、URLConnection、Socket、ServerSocket 等。Java 的 RMI(远程方法激活)机制也是开发分布式应用的重要手段。

  分布式指的是将一个系统拆分成多个独立的子系统或组件,这些子系统或组件分布在不同的计算机节点上,并通过网络进行通信和协作工作。这种架构设计能够提高系统的可伸缩性、可靠性和性能。常见的分布式技术包括服务治理、远程调用、消息队列、负载均衡等。Java中常用的分布式框架有Dubbo、Spring Cloud、Hazelcast等。

3、public、protected、default、private的区别

a) public:成员被声明为public时,表示该成员可以被任何类访问,无论是否属于同一个包。在一个Java源文件中,只能有一个类被声明为public,而且Java源文件的命名为这个被public所修饰的类的类名。

b) protected: 成员被声明为protected时,表示该成员可以被同一个包内的类访问,被不同包中的子类访问需分情况讨论。

(1)子类可以通过继承访问不同包父类的protected成员。

(2)子类可以通过子类的对象访问不同包父类的protected成员。

(3)子类不可以通过父类的对象访问不同包父类的protected成员。

(4)子类不可以通过其他子类的对象访问不同包父类的protected成员。

(5)与子类同包的其他类不可以通过子类的对象访问不同包父类的protected成员。

c) default: 默认访问修饰符,也称为包访问权限,表示该成员可以被同一个包内的类访问,但不能被不同包中的类访问。

d) private: 成员被声明为private时,表示该成员只能被所属类的方法访问,其他类无法访问该成员。

修饰符当前类同一包内子孙类(同一包)子孙类(不同包)其他包
public
protected√ / ××
default××
private××××
 成员指的是类中的属性和方法。类中的成员可以分为实例成员和静态成员。实例成员是每个对象都会拥有的属性和方法,而静态成员是属于类本身的属性和方法,不依赖于对象的创建而存在。成员可以通过访问修饰符进行访问控制,例如public、private、protected等。成员的访问权限取决于其所在类的访问权限和成员本身的访问修饰符。

4、final、finally、finalize的区别

a) final: 关键字,用于修饰类、方法或变量,表示其不可被继承、重写或修改。

(1)修饰类:final修饰的类不能被继承,即不能有子类。

(2)修饰方法:final修饰的方法不能被子类重写。

(3)修饰变量:final修饰的变量必须初始化,所以称为常量,一旦赋值就不能被修改。

b) finally: 一个关键字,用于捕获异常处理中的最后一步操作,只能用在 try/catch 中无论是否发生异常都会执行。finally块中的代码通常用于释放资源、关闭文件或数据库连接等操作。

c) finalize: Object类中的一个方法,每一个对象都有这个方法,一个对象的finalize方法只会调用一次,用于在对象被垃圾回收前执行一些清理操作。finalize方法通常用于释放对象占用的资源,如关闭文件、释放内存等操作。

  调用finalize方法,但并不代表对象一定会被回收。finalize方法是在对象被垃圾回收器回收时才会被调用的,而对象是否会被回收取决于垃圾回收器的算法和策略。因此,即使调用了finalize方法,也不能保证对象会被及时回收。

5、static关键字的作用

当一个对象被创建时,才会为其分配数据存储空间,方法才能被外界调用。但是当没有创建对象的时候,也想访问成员变量或调用方法,此时需要用到static。有了static,使成员变量或者方法成为类级别的成员(而不是对象级别的成员),这样就可以在没有类的时候被访问到了。

(1)静态变量:使用static关键字声明的变量为静态变量,它们存储在静态存储区内,生命周期为整个程序运行期间。静态变量在内存中只有一份副本,意味着无论这个静态变量被实例化多少次,它在内存中只会存在一份。这一份副本会被所有实例共享,当其中一个实例对这个静态变量进行修改时,其他实例也会受到影响。这种共享的特性使得静态变量可以用来在不同实例之间共享数据或状态信息。

(2)静态方法:使用static关键字声明的方法为静态方法,可以直接通过类名调用,无需实例化对象。静态方法不能访问非静态成员变量和方法,只能访问静态成员变量和方法。

(3)静态代码块:使用static关键字声明的代码块为静态代码块,它在类加载时执行,并且只执行一次。静态代码块通常用于初始化静态变量。

(4)静态内部类:使用static关键字声明的内部类为静态内部类,静态内部类可以直接通过外部类的类名访问,无需创建外部类的实例。

  在Java中,实例是指根据类定义创建的具体对象。当一个类被实例化时,就会在内存中分配一块空间来存储该对象的属性和方法。通过实例化,可以创建多个对象,每个对象都拥有自己的属性和方法,但共享同一个类的定义。实例化一个类的过程就是使用关键字" new "来调用类的构造函数,从而在内存中创建一个对象。通过这个对象,可以访问和操作类中定义的属性和方法。因此,实例是类的具体化,是类的具体实体。

MyClass myObject = new MyClass();

上面的代码就创建了一个MyClass类的实例,并将其赋值给myObject变量。这样就可以通过myObject来访问MyClass类的方法和属性。

6、面向对象、面向过程的区别

面向对象和面向过程是两种不同的编程思想。

a) 面向对象是一种以对象为中心的编程思想,将数据封装在对象中,通过对象之间的交互来实现程序的功能。面向对象编程语言具有封装、继承、多等特性,可以设计出低耦合的系统,可以更好地组织和管理代码,提高代码的复用性和可维护性。常见的编程语言有:Java、Python、C++、C#。

b) 向过程是一种以过程或函数为中心的编程思想,程序主要一系列函数或过程组成,通过函数的调用来实现程序功能。面向过程的编程语言的代码结构相对简单。因为没有实例化等操作,开销比较小,适合一些简单、线性的任务。常见的编程语言有:C、Fortran、COBOL。

总的来说,面对象更适合复杂的、大型的开发,可以更好地组织和管理代码;面向过程更适合简单的、型的程序开发,代码结构相对简直观。

  耦合通常用来描述不同系统之间的相互关程度或相互作用程度,是面向对象设计的一个重要原则之一,有助于提高系统的可重用性、可维性和可扩展性。低耦合是指软件系统中个模块之间的依赖关系较弱,模块之间的耦合度低,即模块之间的相互影响较小。低耦合的设计可以使系统更灵活、易于维护和扩展,降低修改一个模块对其他模块造成的影响。

7、变量的类型

  • 局部变量:在方法、构造方法或者语句块中定义的变量被称为局部变量。变量声明和初始化都是在方法中,方法结束后,变量就会自动销毁。
  • 成员变量:成员变量是定义在类中,方法体之外的变量。这种变量在创建对象的时候实例化。成员变量可以被类中方法、构造方法和特定类的语句块访问。
  • 类变量:类变量也声明在类中,方法体之外,但必须声明为 static 类型。

    8、继承、封装、多态

    继承、封装、多态是面向对象编程的三大特性。

    a)继承(Inheritance):一个类可以继承另一个类的属性和方法,从而可以重用已有的代码。子类可以继承父类的属性和方法,并且可以在子类中添加新的属性和方法,从而实现代码的复用和扩展。在Java中,通过extends关键字来实现继承。

    b)封装(Encapsulation):将数据和方法封装在一个抽象的类中,隐藏类的内部实现细节,只暴露一些接口供外部访问。通过封装,可以保护数据的安全性,防止外部直接访问和修改类的属性,提高代码的可维护性和可扩展性。在Java中,可以使用private、protected、public等访问控制符来实现封装。

    c)多态(Polymorphism):一个对象可以以多种形态存在,即一个对象可以被看作是不同类型的实例。多态性使得不同类的对象可以通过相同的接口进行操作,从而实现代码的灵活性和可扩展性。通过多态,可以实现方法的重载和重写,以及接口的实现和继承。在Java中,多态可以通过方法的重载和重写来实现。

     多态的实现依赖于继承,继承是实现多态的一种方式。通过继承,子类可以重写父类的方法,从而实现多态。

    9、实现多态的三个必要条件

    a)继承:在多态中,必须存在有继承关系的子类和父类。

    b)重写:子类实现了父类中的同名方法,但对方法进行了重新的定义,实现方式可能不同。

    c)向上转型:将一个子类对象转换为其父类类型的过程。通过将子类对象赋值给父类引用,这样既可以调用父类的方法,也可以调用子类的方法。

    10、重写和重载的区别

    重写是在继承关系中子类重新定义父类方法的过程(运行时),而重载是在同一个类中定义多个方法来实现同一种功能的不同版本(编译时)。重写是实现多态性的一种方式,而重载可以提高代码的灵活性和可读性。

    a)重写(Override):子类重新定义父类中已经存在的方法,以实现子类特有的功能。在重写中,方法的名称、参数列表和返回类型必须与父类中的方法相同,但方法体可以有所不同(外壳不变,核心重写)。重写是实现多态性的一种方式,通过子类对象调用重写的方法时,会执行子类中的方法,而不是父类中的方法。

    b)重载(Overload):在同一个类中定义多个方法,它们具有相同的名称但参数列表不同,返回类型可以相同也可以不同,以实现同一种功能的不同版本。每个重载的方法必须有一个独一无二的参数列表,编译器会根据方法的参数列表来决定调用哪个重载方法。

    感谢您的观看,希望你今天特别特别开心,加油~