- java 的平台无关性
- 面向对象
- Java 的语言特性
- java 类库
- GC
对于 Java 的理解,每个程序员都会有不同的见解,而且能够说出很多不同维度的理解,如果发散开来一篇文章是说不完的。 所以,本文主要是从 Java 的几点特性出发,简单的聊聊对 Java 的理解, 会不断的补充进来
一、Java 的平台无关性
Java 平台无关性简单理解就是一次编译到处运行,即平台无关性。那么问题来了,java 是如何实现平台无关性的?
通常 Java 程序运行会分为编译期和运行时
- 编译期:通过 Javac 指令,编译是指编译 Java 的源码(.java文件编写的),将源码编译生成字节码(存入到对应的.class文件),
- 运行时:通过 Java 指令执行字节码文件;(将字节码翻译成对应平台的机器码)
反编译:Javap 指令是jdk自带的反汇编器,可以查看Java编译器为我们生成的字节码; Javap -c 对字节码代码进行反汇编,将从*.class到可执行程序的过程逆过来, 查看 javac 生成的 class 文件的内容,就是将二进制文件转成 class 文件的过程;
实践:下面给出一段代码,然后简单介绍一下这段代码的执行过程:
public class ByteCodeTest {
public static void main(String[] args) {
int i = 1;
int j = 5;
i++;
System.out.println(i);
System.out.println(j);
}
}
javac 指令的执行方式:
javac + 类所在的文件路径 + 类名.java
执行会在与 *.Java 文件相同路径下生成 *.class 文件
生成的 class 文件:
//
// Source code recreated from a .class file by IntelliJ IDEA
// (powered by Fernflower decompiler)
//
package com.ercargo.learn.concurrency.javabasic;
public class ByteCodeTest {
public ByteCodeTest() {
}
public static void main(String[] var0) {
byte var1 = 1;
byte var2 = 5;
int var3 = var1 + 1;
System.out.println(var3);
System.out.println(var2);
}
}
反编译的过程解析一下 class 文件:
- javap 是 jdk 自带反汇编器, 可以查看 java 编译器为我们生成的字节码;
ps: 以上就是 java 虚拟机( HotSpot )所能理解的字节码
上述过程中 .class 文件中的字节码是 java 跨平台的核心和基础,Java 虚拟机可以解析该文件,转换成特定平台的执行指令(Linux,Windows,MacOS)
总的来说:Java 提供了各种不同平台上的虚拟机,jvm 可以将字节码文件加载到内存,并最终转换成当前操作系统能够识别的机器码去执行,从而实现了平台无关性;
二、面向对象
Java 具有面向对象语言的基本特性,封装、继承、多态,这里简单给出一点自己的见解,详细理解可以参考: 《Thinking in java》
- 封装: 封装是抽象具有相同特性和行为的对象集合,理解成对类的内部实现进行隐藏,对外界只暴露该类的访问方法
- 继承: 基类重用超类代码
- 多态: 后期绑定/动态绑定,OOP 中,程序直到运行时才能确定代码的地址,所以必须通过动态绑定,当像对象发送消息时,被调用的代码直到运行时才能确定。
涉及到泛型的概念
注意这里有一个问题,我们在真正写代码的时候会经常用继承吗?继承会导致一些什么问题?
《Effective Java》中提出一个概念:组合优于继承
为什么说组合优于继承呢?
继承:子类继承父类,即父类的内部细节(方法和属性)对子类都是可见的,如果父类发生改变,子类必然也要随之改变,所以会造成代码的耦合度非常高 而且破坏代码的封装性,一般除了使用多态的情况(需要从新类向基类进行向上转型),或者父类完全不会改变的情况(确认基类与超类之间存在的只有is-a的关系), 都是不推荐使用继承的; 组合是将现有对象进行拼装产生新的更复杂的功能,类的组合关系一般在运行期确定,如下面这段代码: ``` public class Teacher { private double salary; /** * 将User和Teacher 组合,而不是Teacher继承User, * User中的其他属性修改,不会直接影响Teacher */ private User user;
public double getSalary() {
return salary;
}
public void setSalary(double salary) {
this.salary = salary;
}
public String getName(){
return user.getName();
} } ```
三、Java 语言特性
关于 Java 的语言特性,主要包括:泛型,反射,java8 提供的 Lambda 表达式等
本文简单介绍一下 java 的泛型和反射,后面深入学习之后再作总结。
- Java 泛型,简单的理解就是将原先具体的参数类型的定义泛化,编译器负责转成特定类型。多态实际上就是一种泛化机制。
- Java 反射: 程序运行时,对任意一个类可以获取到类中的属性,方法; 对任意一个对象,可以调用他的方法。
- Java8 Lambda 表达式,支持函数式编程
四、Java基础类库
Java 的类库有很多很多,这里主要指的是JDK中包含的基础类库,源码下载:jdk
比较重要的有:java 集合,java 并发库(J.U.C), 网络库,IO,NIO 等等
本文就不一一展开介绍,后续文章中会依次对这些重要的包进行总结。
五、GC
GC 是 Java 特性中的重点,也是面试经常被问到的问题。 GC 简单来说就是 java 的垃圾回收,但是里面包含的内容非常多。谈到 GC, 必然要知道 JVM 的工作原理,内存结构。 在《聊聊 GC》这一篇中将会进行详细介绍。
文章内容主要是对自己学习的总结,还有很多需要深入挖掘的内容,To Be Continue
[参考引用]
- 《Thinking in Java》
- 《剑指Java面试》
- 《Effective Java》