1. 概述

在这个教程中,我们将学习如何通过命令行界面与Java编译器交互。

在开始之前,我们需要确保已经安装了Java,并在机器上配置了JAVA_HOME环境变量。

2. 单个Java源代码文件的编译

Java提供了一个简单的工具——javac,用于编译Java源代码文件。我们先从编译一个简单的类,Car.java 开始:

public class Car {
    private String make;
    private String model;

   // standard setters and getters
}

我们可以在该文件所在的目录中使用单条命令进行编译:

javac Car.java

如果一切顺利,没有错误,将不会有任何输出。编译器会在当前工作目录下生成包含字节码的Car.class 文件。

3. 多个源代码文件的编译

通常,我们的程序会使用多个类文件。现在让我们看看如何编译一个包含多个类的简单程序。

首先,添加两个新类型:Owner.javaHistory.java

public class Car {
    private String make;
    private String model;
    private Owner owner;
    private History history;
}
public class Owner {
    private String name;
}
public class History {
    private String details;
}

现在,我们需要运行以下命令进行编译:

javac Owner.java Car.java History.java

需要注意的是,由于Car 类使用的类都在同一目录下,指定它们实际上是可选的。 我们仍然可以直接编译Car.java

4. Java编译器的基本选项

到目前为止,我们只是通过参数传递类名的方式使用javac命令,而没有额外的选项。但也可以进行自定义。我们可以告诉Java编译器查找我们的库类的位置、代码所在的根路径,以及最终结果的生成位置。

让我们更深入地了解其中一些选项。

  • --cp--classpath
  • --sourcepath
  • --d (目录)

4.1. 什么是--cp*或--classpath选项?*

使用类路径,我们可以定义一组依赖于编译时的目录或文件,如*.jar*.zip。或者,可以通过设置CLASSPATH环境变量来指定。

需要注意的是,类路径选项的优先级高于环境变量

如果没有指定,类路径默认为当前目录。当需要指定多个目录时,对于大多数操作系统(除Windows外),路径分隔符是*:*,而在Windows上是*;*

4.2. 什么是*--sourcepath*选项?

这个选项使得我们可以指定所有需要编译的源代码的顶级目录。

如果不指定,编译器会扫描类路径寻找源代码。

4.3. 什么是*--d*选项?

当我们希望所有编译结果都放在一个地方,且与源代码分开时,使用此选项。我们需要记住,要指定的路径必须事先存在

在编译过程中,这个路径被用作根目录,根据类的包结构自动创建子目录。如果没有指定此选项,每个*.class文件将被写入其对应*.java源文件旁边。

5. 使用外部库进行编译

除了我们创建的类之外,我们的程序还需要使用外部库。现在让我们看一个更复杂的例子:

libs/
├─ guava-31.1-jre.jar
model/
├─ Car.java
├─ History.java
├─ Owner.java
service/
├─ CarService.java
target/

在这里,我们按照包组织了类。此外,我们添加了targetlibs目录,分别用于存放编译结果和库。

假设我们要使用Guava库提供的ImmutableSet类。我们下载并将其放在libs文件夹中。然后,在service包中,我们在CarService.java中引入一个使用外部库的新类:

package service;

import model.Car;
import java.util.Set;

import com.google.common.collect.ImmutableSet;

public class CarService {

    public Set<Car> getCars() {

        Car car1 = new Car();
        Car car2 = new Car();

        ImmutableSet<Car> cars = ImmutableSet.<Car>builder()
          .add(car1)
          .add(car2)
          .build();
        return cars;
    }
}

现在,是时候编译我们的项目了:

javac -classpath libs/*:. -d target -sourcepath . service/CarService.java model/*.java

我们在类路径中包含了libs文件夹,使用-\-cp

libs/
├─ guava-31.1-jre.jar
model/
├─ Car.java
├─ History.java
├─ Owner.java
service/
├─ CarService.java
target/
├─ model/
│ ├─ Car.class
│ ├─ History.class
│ ├─ Owner.class
├─ service/
│ ├─ CarService.class

如我们所见,javac成功解析了外部的ImmutableSet类,并将编译后的类放在target文件夹中。

6. 总结

在这篇文章中,我们学习了如何编译多个源代码文件,即使它们依赖于外部库。

此外,我们还快速了解了一些在复杂编译任务中可以利用的关键选项。


« 上一篇: Spark DataFrame
» 下一篇: 用Java交换两个变量