Все знают, как компилировать исходный код Java, а именноcmdперейти в каталог, где находится исходный файлjavac **.javaи всё. Когда в программе есть объявление пакета, можно ли всё ещё просто напрямуюjavac **.java? Ответ, конечно,нет, ниже простой пример, доказывающий, что происходит при прямойjavac **.javaкомпиляции этого.

Как показано ниже: в каталоге F:\javaweb2班\20160531 есть файл A.java. Обратите внимание, что исходный файл содержит объявление пакета:

Пример

package mypack; public class A { String name; int age; public void setName(String _name){ this.name =_name; } public void setAge(int _age){ this.age = _age; } public String getName(){ return this.name; } public int getAge(){ return this.age; } public static void main(String[] args){ A a = new A(); //a.setName("zs"); a.name="zs"; a.setAge(18); System.out.println(a.getName()+a.getAge()); } }

Теперь скомпилируйте A.java напрямую с помощью javac A.java, и результат будет следующим:

Мы ясно видим, что файл байт-кода A.class появился в текущем каталоге. Можно ли его так напрямую запустить? Давайте попробуем!

Эта ошибка появилась, потому что в A.java есть объявление пакета. При выполнении исходного файла A.java виртуальная машина Java сначала ищет файл байт-кода в текущем каталоге A.java. Хотя на этот раз она его находит, поскольку в A.java есть объявление пакета, затем виртуальная машина Java переходит в каталог пакета, чтобы найти файл байт-кода A.class. Только когда она найдёт его там, она сможет успешно выполниться. Если не верите, давайте проведём эксперимент! (Здесь я также научу вас, как скомпилировать A.java с объявлением пакета, то есть пакетную компиляцию с помощью javac -d . A.java)

Теперь пакетная компиляция успешно завершилась. На данном этапе видно, что файл A.class появился в каталоге mypack. Давайте попробуем его выполнить.

На этом этапе мы обнаруживаем, что выполнение всё ещё не удаётся?? Почему так?? Это проблема, с которой сталкиваются многие новички. Здесь всем нужно запомнить один момент: параметр команды Java — это "полное имя класса", а не "имя файла".

Полное имя класса этой исходной программы должно быть mypack.A, поэтому это следует записать так:java mypack.A

Теперь это может успешно выполниться!

Не спешите!! Ниже есть кое-что поинтереснее! Что касается использования пакетов, как же не объяснить импорт пакетов, их создание и компиляцию!

На этот раз мы вводим ещё один тестовый класс Test.java со следующим кодом:

Пример

import mypack.A; public class Test{ public static void main(String[] args){ A a = new A(); a.setName("zs"); //a.name="zs"; a.setAge(18); System.out.println(a.getName()+a.getAge()); } }

Скомпилируйте и выполните следующим образом:

Результат, как и ожидалось, конечно же, таков: всё компилируется и выполняется. Ход выполнения выглядит так: после компиляции Test.java сгенерированный файл байт-кода находится в текущем каталоге (во время компиляции он проверяет, есть ли файл A.class в mypack; если нет, компиляция завершается неудачей). Во время выполнения, поскольку в Test.java нет объявления пакета, виртуальная машина Java сначала находит Test.class в текущем каталоге и выполняет его. Когда выполнение доходит до места, где в программе ссылаются на класс A, виртуальная машина Java проверяет, есть ли файл байт-кода A.class в текущем каталоге. В этот момент, даже если она его находит, она войдёт в пакет в соответствии с импортом пакета в исходной программе, чтобы искать A.class. Только когда она его найдёт, выполнение сможет завершиться успешно (фактически она уже искала его на этапе компиляции!)

Пойдём дальше: если мы добавим объявление пакета package mypack1; в тестовый класс Test.java,

Теперь выполним пакетную компиляцию Test.java. Здесь я хочу снова пояснить два момента: 1. При пакетной компиляции каталог пакета создаётся автоматически, и вам не нужно самому создавать папку с именем пакета; 2. Когда в текущем каталоге есть несколько java-файлов, которые нужно скомпилировать или пакетно скомпилировать,javac -d . *.javaКоманда может скомпилировать или пакетно скомпилировать все java-файлы в текущем каталоге в зависимости от того, есть ли в программе объявление пакета.

Теперь как нам выполнить файл Test.java? java Test.java? Очевидно, это не сработает. Вспомните, что я говорил ранее: параметр команды Java — это «полное имя класса», а не «имя файла».

Следовательно, нам нужно выполнить это так:

Таким образом:

Всё, что обсуждалось выше, — это общий случай, то есть classpath находится в текущем каталоге. Когда classpath не в текущем каталоге, можно ли всё ещё это выполнить? И как это следует выполнять?

Как показано на рисунке ниже, я поместил Test.java в каталог на один уровень выше. В этом случае нам нужно самим задать параметр classpath. Например:F:\\javaweb2班>java -cp F:/javaweb2class/20160531 mypack1.java; или в любом каталоге:java -cp F:/javaweb2class/20160531 mypack1.java

Таким образом, всё получается! Все, проанализируйте и разберитесь в конкретном процессе выполнения самостоятельно!

Итог

    1. Параметр команды Java — это «полное имя класса», а не «имя файла».
  • 2. При пакетной компиляции каталог пакета создаётся автоматически, и вам не нужно самому создавать папку с именем пакета.
  • 3. Когда в текущем каталоге есть несколько java-файлов, которые нужно скомпилировать или пакетно скомпилировать,javac -d . *.javaКоманда может скомпилировать или пакетно скомпилировать все java-файлы в текущем каталоге в зависимости от того, есть ли в программе объявление пакета.
  • 4. Когда classpath не находится в текущем каталоге, нужно использоватьjava -cp ..., например:java -cp F:/javaweb2class/20160531 mypack1.java。
  • 5. Разберитесь в процессе, с помощью которого виртуальная машина Java выполняет файлы байт-кода на основе объявлений пакетов и импорта пакетов.

Исходный адрес: https://www.cnblogs.com/xiaoming0601/p/5551113.html