Day3|Hello World 背后的故事

lazysnail2025/07/08Java基础

作为很多语言入门教程的第一代码 ,在 Java 世界中,也以Hello,World作为我们的第一行代码。

但我们今天不止是输出一句话,而是要带你理解它背后的整个流程:

Java 程序是如何被写出来、编译、再一步步被执行的?

一、写下第一个 Java 程序

第一种方式

创建源码文件

用任意文本编辑器(如Notepad++/Windows记事本)新建文件:HelloWorld.java(注意保存时文件后缀是.java)

img

注意代码中class后的类名与文件名一致

img

全部代码必须写在类中(class 是基本单元)

main 方法是 JVM 定义的程序入口

System.out.println(...):向控制台输出一行文本

编译源代码

打开命令行,进入代码文件所在目录,保存的位置自行选择(最好是全英文的目录)

img

执行:

javac HelloWorld.java

然后执行dir命令,列出目录下所有文件,会发现产生了一个HelloWorld.class文件

img

这个class后缀的文件也就是我们最常说的字节码文件。

可以这样理解:

.java文件是我们能够认识的源码(任何字符、符号、逻辑),我们都有清晰的认知。

javac将.java文件按照一定的规则翻译(转换)成了JVM认识的文件内容。

当把字节码文件交给JVM的时候,JVM执行的内容就是字节码。

如果你尝试直接使用Notepad++打开class文件,你会看到下面的场景:

img

一堆乱码,偶尔能看到几个熟悉的单词。

如果你用UltraEdit打开字节码文件,并切换到16进制模式,你会看到如下场景:

img

如果你对字节码文件的内容很感兴趣,你可以尝试去阅读jvms17open in new window

这个章节中专门描述了字节码文件的构成,后续的章节会详细的讲到。

运行

执行如下命令:

java HelloWorld

img

java命令可以理解为将字节码文件交给JVM运行,运行的结果就是在命令行窗口输出了"Hello, World!"。

通过以上三步,从代码编写、编译、运行,一个完整的Java程序运行周期基本都体现出来了。

反编译

上文中提到,我们如果直接打开字节码文件,内容是不适合人类阅读的。

JDK提供了一个反编译工具(javap)。

在刚才的目录执行:

javap -c HelloWorld

img

javap -c 会将字节码转换成人类可读的 JVM 指令。

这些指令,你需要去指令集open in new window查找。

比如:

img

详细的指令在后续的文章中也会讲到。

第二种方式

创建包、类

Day2的文章中,我们已经大致的讲了一下IDEA的使用过程。

这次我们直接新建一个package:

img

包名:com.lazy.snail.day3(可以自定义)

img

然后在包内新建一个类文件:

img

创建好之后的样子:

img

直接在大括号中编写代码:

public static void main(String[] args) {
	System.out.println("Hello, World!");
}

编译源代码

直接build项目,源代码则会编译成字节码文件,不需要我们再输入javac命令,这些动作IDE已经帮我们完成,内嵌到某些按钮里面。

img

之前执行javac时,产生一个.class字节码文件,那么通过IDE编译的字节码在哪儿?

打开File-->Project Structure

img

然后找到编译文件的输出目录(这个目录也是可以自定义的,一般在项目根目录下有个默认值)

img

找到这个目录,字节码文件就在此处:

img

还有一个简便的方法:

img

勾选上Excluded Files,左侧是项目文件结构中就会出现一个编译文件的输出目录。

运行

IDE中怎么运行代码呢?还需要手敲java命令吗?

当然不需要了,IDE已经帮我们集成了。

这两个三角符号,都可以直接运行代码:

img

其实上一步的编译也可以忽略,直接点击三角符号,IDE会在运行前进行编译。

反编译

这里推荐一个IDEA的插件jclasslib

插件下载:File-->Settings-->Plugins-->Marketplace

直接搜索jclasslib安装即可。

img

使用:

打开jclasslib视图

img

右侧的jclasslib展示框会展示出这个类的所有信息(包括方法的字节码指令、类相关信息等)

img

在后续的学习过程中,会时不时的用上这个插件。

二、main方法

接下来我们大致的看一下main方法的代码

public static void main(String[] args){
    // 具体逻辑
}

这个main方法是Java 程序的入口方法,是 JVM(Java 虚拟机)执行程序时第一个调用的方法。它的语法和签名是固定的,必须严格按照以下格式定义:

public是访问修饰符:表示该方法是公开的,可以被 JVM 从类的外部访问。

static是静态方法修饰符:表示该方法是静态的,属于类本身,而不是类的实例。

void是返回类型:表示该方法没有返回值。

main是方法名:这是 Java 语言规定的入口方法名称,不可更改。

String[] args是接受参数:接收命令行参数。args是一个字符串数组,表示运行程序时传入的参数。

三、执行流程

这张图大致的描述了源代码(.java)到字节码(.class)再到JVM运行的过程

img

四、一次编写,到处运行

这句话相信大家都听过,Java可以一次编写,到处运行,体现Java的跨平台性。

从上面简单的Hello,World程序,其实我们也能窥见一二。

开发者编写的 Java 代码,都会使用javac编译器将 .java文件编译成与平台无关的字节码(一种中间代码)。

字节码不是针对特定操作系统的机器码,而是面向 JVM 的指令集,格式统一(类似“通用机器语言”)。

不同操作系统(Windows、Linux、macOS 等)需要安装对应版本的 JVM。JVM 负责将字节码转换为当前平台的本地机器码,并执行它。(当学到JVM,接触虚拟机实现时,你就会发现,真正与平台相关的代码JVM实现已经帮我们处理了)

小结一下为什么Java能够实现“一次编译,到处运行”。

统一标准

字节码是平台中立的,所有 JVM 遵循相同的字节码规范(由 Java 虚拟机规范定义)

不同平台的 JVM 负责将同一份字节码“翻译”成本地机器码,开发者无需针对不同平台重新编译代码。

结语

  • 第一次写下完整的 Java 程序
  • 熟悉了源文件、编译、运行流程
  • 明白了 Java 程序从源码到执行的幕后过程
  • 学会使用命令行和IDEA两种方式运行代码
  • 对main方法的结构与意义有了清晰认识

最后强烈推荐大家在学习过程中,多翻看官方文档open in new window

最后更新 7/10/2025, 11:14:05 AM