一起养成写作习惯!这是我参与「掘金日新计划 · 4 月更文挑战」的第5天,点击查看活动详情。
日常使用 java 时,由于其语言静态性,往往需要编译和打包才能调用,这还是比较麻烦的,虽然 jdk9 以后提供了 jshell 来简化测试,但是以目前商业情形,大部分还是停留在 jdk8 的版本,所以快速打包代码测试,成了一个 javaer 必备的能力。
1. WIN 环境执行 java 单文件
1. class 方式
最简单的方式,如果只是在本机环境下测试,无需打包,直接可以使用编译后文件进行测试。
1. 编写
首先需要编写代码,保证 import 等信息正确
public class Hello{
public static void main(String[] args){
System.out.println("Hello World");
}
2. 编译
在文件所在文件夹,使用 javac ,可生成 class 文件
> javac Hello.java
3. 执行
此时可以测试,执行 class 文件
> java Hello
2. jar 方式
有时候,代码需要放到不同设备上执行,此时就需要压缩成 jar 模式,方便设备适配和移动。
1. 编写
代码同上
2. 编译
打包 jar 文件时,必须增加清单文件,首先在该文件目录下新建一个 manf 的文件清单,内容为指定主类
# manf
Main-Class: Hello
注意清单文件的规范,在冒号后面要有一个空格,行末不能有空格,最后一行是空行
> jar cvfm Hello.jar manf Hello.class
3. 执行
打包之后会生成一个 Hello.jar 文件,执行
> java -jar Hello.jar
2. 多文件之引用 class 文件打包
当文件需要引用多个 class 文件时,就需要将所有相关文件压缩到一起。
一般的文件结构
│ Hello.java
├─test
│ │ Gen.java
1. 编写
编写程序,此时需要引用另外一个包的方法。
# Hello.java
import test.Get;
public class Hello{
public static void main(String[] args){
Get aget=new Get();
aget.print();
}
}
# Get.java
package test;
public class Get{
public void print(){
System.out.println("Good Job");
}
}
2. 编译
在 Hello.java 中 import test.Get 中将 test 作为包处理,所以需要在该文件中加上 package test 才能编译成功
> jar cvfm Hello.jar manf Hello.class test/Get.class
3. 执行
> java -jar Hello.jar
3. 多文件之引用 jar 打包
文件结构同上,但删除 test 及其下文件
1. 编译
当我们编译 Hello.java 时报错,因为找不到 test 包下面的 Get.class 的文件,但是 Hello.jar 内有 test.Get,因此打包时候需要将其引进来
# -cp:在java文件中,引入其他的jar包,多个jar包用分号隔开
> javac -cp Hello.jar Hello.java
此时会生成 Hello.class 文件,但执行需要增加 classpath 参数
# -classpath:要编译或执行的类引用了其它的类,但被引用类的.class文件不在当前目录下时,就需要通过-classpath来引入类
> java -classpath Hello.jar Hello
在清单文件中指明类加载路径,将 jar 的路径包含进来,避免找不到类的错误
# manf
Main-Class: Hello
Class-Path: Hello.jar
打包
> jar cvfm a4.jar manf Hello.class
2. 执行
> java -jar a4.jar
注意
Main-Class中类如果有限定名,则写成全限定名,比如package.classnameClass-Path中引用多个jar包,则以换行分隔多个jar包的相对路径
4. Linux 下执行 jar 文件
1. java - jar
执行该命令时,会用到目录 META-INF\MANIFEST.MF 文件,在该文件中,有一个叫 Main-Class 的参数,它说明了 java -jar 命令执行的类
2. java -cp
指定类运行所依赖其他类的路径,通常是类库、jar包之类,需要全路径到jar包,表达式支持通配符
java -cp (jar包路径:...) (主类的全限定名称) (参数)