25   環境變數及命令列變數、選項引數設定

之前於「開發環境」章節中已簡單說明過環境變數,但環境變數及其引數甚為繁雜,特闢專章說明,主要以Windows 7為例。

Windows 710可進入[控制台] ->[系統及安全性]->[系統]->[進階]->[環境變數]新增環境變數或編輯現有環境變數,選擇user的使用者環境變數時,效用僅限於該使用者,如選擇系統環境變數,則適用於全部使用者。

環境變數有PATHCLASSPATH等,並有命令列選項引數-sourcepath-d,其關係圖如下,功能及使用方式詳述如後。

 

 圖 25-1各環境變數、引數關係圖               

[25-1 PATH環境變數]

為作業系統使用之環境變數,設定Windows執行檔.exebat之搜尋路徑,編譯程式javac.exe及執行程式java.exe須放置於該路徑上方可執行。

環境變數名稱:PATH

變數值:C:\Program Files\Java\jdk1.8.0_11\bin等。(預設C:\Windows\system32)

binJDK下載後放置javac等之資料夾。jdk資料夾名稱視下載時版本而定。

適用時機為執行javac時,會自動搜尋此一資料夾。

定義多個變數值時,須以;(分號)隔開,並會依序尋找,使用第一個找到者。

[javacjava]

程式名

安裝後之PATH

備註

javac

C:\Program Files\Java\jdk1.8.0_11\bin

紅字部分依版本而異

java

C:\Windows\system32

預設

 

 圖25-2 各環境變數、引數關係圖(PATH) 

 

[25-1-1 PATH設定方式]

[命令列變數]

使用命令列set指令設定PATH,可設定多個值,搜尋時會依序尋找,使用第一個找到者。以命令列指令設定者,優先於系統環境變數及使用者環境變數所設定者。有效期間為設定後直到命令列關閉,下次開啟命令列時須重新設定。

設定例:假設欲編譯之原始程式碼Main22.java存放於C:\js資料夾,但未設

定編譯程式javacPATH,則須指定完整路徑。

<錯誤(未設定)>C:\js>javac main22.java.....找不到javac

<正確(未設定)>C:\js>"C:\Program Files\Java\jdk1.8.0_11\bin \javac" main22.java

<正確>C:\js>set PATH=C:\Program Files\Java\jdk1.8.0_11\bin

C:\js>javac main22.java

 

[系統環境變數]

Windows 710可進入[控制台] ->[系統及安全性]->[系統]->[進階]->[環境變數]新增或編輯系統環境變數PATH,尚未設定其他變數值時使用新增功能,已有設定者使用編輯功能插入變數值。可設定多個值,以;(分號)區隔,搜尋時會依序尋找,使用第一個找到者,常用者可置於前面。系統環境變數優先於使用者環境變數。

新增或編輯例:輸入C:\Program Files\Java\jdk1.8.0_11\bin

命令列編譯輸入例:C:\js>javac main22.java

 

[使用者環境變數]

Windows 710可進入[控制台] ->[系統及安全性]->[系統]->[進階]->[環境變數]新增或編輯使用者環境變數PATH。尚未設定其他變數值時使用新增功能,已有設定者使用編輯功能插入變數值。可設定多個值,以;(分號)區隔,搜尋時會依序尋找,使用第一個找到者,常用者可置於前面。

新增或編輯例:輸入C:\Program Files\Java\jdk1.8.0_11\bin

命令列編譯輸入例:C:\js>javac main22.java

 

[環境變數編輯範例]

原有變數值:C:\Windows\system32

編輯後變數值:C:\Program Files\Java\jdk1.8.0_11\bin;C:\Windows\system32

(插入紅字部分)

 

 

[25-1-2 PATH的選擇原則]

PATH的選擇原則如下圖:

圖25-3 PATH的選擇原則   

 

[25-2 CLASSPATH]

JVM使用之環境變數。指定原始程式碼編譯(javac指令)時及執行(java指令)時,位元檔(.class)的輸入來源資料夾,而非輸出資料夾。

環境變數名稱:CLASSPATH

變數值:自定,預設為目前的資料夾

適用時機為javac編譯或java執行時指定byte code(.class)之輸入路徑。

 圖25-4 各環境變數、引數關係圖(CLASSPATH)  

 

[25-2-1 CLASSPATH設定方式]

[命令列選項引數]

使用命令列選項引數-cp(classpath)設定CLASSPATH,可設定多個值,以;(分號)區隔,搜尋時會依序尋找,使用第一個找到者。以命令列選項引數設定者,優先於命令列變數、系統環境變數及使用者環境變數所設定者。有效期間為該次執行javacjava指令,下次執行時須於javacjava指令再指定該選項引數。

 

圖25-5 CLASSPATH範例目錄結構   

指定格式:javac |java  -cp  資料夾  主類別名稱

指定例:C:\js1>java –cp npub1 npubMain22

資料夾指定格式可分為相對位置及絕對位置,如目前資料夾為C:\js1

相對位置例(同上)C:\js1>java –cp npub1 npubMain22

絕對位置例:C:\js1>java –cp C:\js1\npub1 npubMain22

 

[命令列變數]

使用命令列set指令設定CLASSPATH,可設定多個值,以;(分號)區隔,搜尋時會依序尋找,使用第一個找到者。以命令列指令設定者,優先於系統環境變數及使用者環境變數所設定者。有效期間為設定後直到命令列關閉,下次開啟命令列時須重新設定。

指定格式:set  classpath=資料夾

指定例:C:\js1>set classpath=npub1

        C:\js1>java npubMain22

資料夾指定格式可分為相對位置及絕對位置,如目前資料夾為C:\js1

相對位置例:C:\js1>set classpath=npub1

絕對位置例:C:\js1>set classpath=C:\js1\npub1

 

[系統環境變數]

Windows 710可進入[控制台] ->[系統及安全性]->[系統]->[進階]->[環境變數]新增或編輯系統環境變數CLASSPATH可設定多個值,以;(分號)區隔,搜尋時會依序尋找,使用第一個找到者。系統環境變數優先於使用者環境變數。

系統環境變數CLASSPATH新增及編輯方式同PATH

 

[使用者環境變數]

Windows 710可進入[控制台] ->[系統及安全性]->[系統]->[進階]->[環境變數]新增或編輯使用者環境變數CLASSPATH可設定多個值,以;(分號)區隔,搜尋時會依序尋找,使用第一個找到者。

使用者環境變數CLASSPATH新增及編輯方式同PATH 

 

[25-2-2 CLASSPATH的選擇原則]

CLASSPATH的選擇原則如下圖:

圖25-6 CLASSPATH的選擇原則   

 

[25-2-3 編譯時.class檔之輸出資料夾]

執行javac編譯時,其.java來源資料夾依後述SOURCEPATH選擇原則,.class輸出資料夾則為當時資料夾或依-d選項引數指定。

 

圖25-7 -d選項引數範例目錄結構  

 

[原始碼檔內容]

檔名:class_m1.java

class class_a1 {  int x = 10;  }

class class_m1{

  public static void main(String[] args){

    class_a1 obj1 = new class_a1();

    obj1.x = obj1.x + 1;

    System.out.println("x的值為" + obj1.x);  }

檔名:class_m2.java

class class_a2 {  int x = 10;  }

class class_m2{

  public static void main(String[] args){

    class_a2 obj1 = new class_a2();

    obj1.x = obj1.x + 2;

    System.out.println("x的值為" + obj1.x);  } }

檔名:class_m3.java

class class_a3 {  int x = 10;  }

class class_m3{

  public static void main(String[] args){

    class_a3 obj1 = new class_a3 ();

    obj1.x = obj1.x + 3;

    System.out.println("x的值為" + obj1.x);  } }

檔名:class_m4.java

class class_a4 {  int x = 10;  }

class class_m4{

  public static void main(String[] args){

    class_a4 obj1 = new class_a4 ();

    obj1.x = obj1.x + 4;

    System.out.println("x的值為" + obj1.x);  } }

 

[原始碼、位元碼皆位於執行時資料夾-不指定-d選項引數時]

原始碼來源資料夾js1class_m1.java

位元碼輸出資料夾js1class_m1.classclass_a1.class

 圖25-8 原始碼、位元碼皆位於執行時資料夾  

 

[執行例]

C:\js1>javac class_m1.java

C:\js1>java class_m1

x的值為11

 

[原始碼位於執行時資料夾,位元碼置於指定-d選項引數之資料夾-相對路徑]

-d所指定之資料夾必須為已經存在。

原始碼來源資料夾js1class_m2.java

位元碼輸出資料夾js1\npub1class_m2.classclass_a2.class

 

圖25-9原始碼位於執行時資料夾,位元碼資料夾以-d指定-相對路徑   

 

[執行例]

C:\js1>javac -d npub1 class_m2.java

C:\js1>cd C:\js1\npub1

C:\js1\npub1>java class_m2

x的值為12

 

[原始碼位於執行時資料夾,位元碼置於指定-d選項引數之資料夾-絕對路徑1]

-d所指定之資料夾必須為已經存在。

原始碼來源資料夾js1class_m3.java

位元碼輸出資料夾js1\npub1class_m3.classclass_a3.class

 

圖25-10原始碼位於執行時資料夾,位元碼資料夾以-d指定-絕對路徑1   

 

[執行例]

C:\js1>javac -d C:\js1\npub1 class_m3.java

C:\js1>cd C:\js1\npub1

C:\js1\npub1>java class_m3

x的值為13                                

 

[原始碼位於執行時資料夾,位元碼置於指定-d選項引數之資料夾-絕對路徑2]

-d所指定之資料夾必須為已經存在。

原始碼來源資料夾js1class_m4.java

位元碼輸出資料夾ctcsource1class_m4.classclass_a4.class

 

圖25-11原始碼位於執行時資料夾,位元碼資料夾以-d指定-絕對路徑   

 

[執行例]

C:\js1>javac -d C:\ctcsource1 class_m4.java

C:\js1>cd C:\ctcsource1

C:\ctcsource1>java class_m4

x的值為14

 

 

[25-2-4 javacjava指令與CLASSPATH]

java程式編譯及執行時以classpath指定位元檔之來源資料夾。

 

原始碼來源資料夾js1cpsub1.javacpmain1.java

位元碼輸出資料夾js1\npub1cpsub1.class

 

//檔名cpsub1.java,資料夾C:\js1

public class cpsub1 {

  int a = 10;

  void pr1() {

    System.out.println("a = " + a);  }  }

//檔名cpmain1.java,資料夾C:\js1

class cpmain1 {

 public static void main(String[] args){

    cpsub1 ph = new cpsub1();

    ph.pr1();  }  }

 

[編譯時指定輸出資料夾]

C:\js1>javac -d npub1 cpsub1.java

將資料夾js1cpsub1.java編譯至資料夾js1\npub1cpsub1.class

 

 圖25-12 編譯時指定輸出資料夾  

   

[編譯時不指定輸出資料夾]

C:\js1>javac cpmain1.java

將資料夾js1cpmain1.java編譯至資料夾js1cpmain1.class,因未指定classpath而找不到cpsub1.class,故會將資料夾js1內之cpsub1.java再編譯至同一資料夾js1內。

 

圖25-13 編譯時指定輸出資料夾   

   

C:\js1>java cpmain1

a = 10

 

 

刪除資料夾js1中之cpsub1.javacpsub1.classcpmain1.class

[範例-錯誤]

C:\js1>javac cpmain1.java

將資料夾js1cpmain1.java編譯,因找不到cpsub1.classcpsub1.java,因而編譯錯誤。

                   

C:\js1>javac cpmain1.java

cpmain1.java:3: error: cannot find symbol

    cpsub1 ph = new cpsub1();

    ^

  symbol:   class cpsub1

  location: class cpmain1

cpmain1.java:3: error: cannot find symbol

    cpsub1 ph = new cpsub1();

                    ^

  symbol:   class cpsub1

  location: class cpmain1

2 errors              

 

圖25-14   

[範例]

C:\js1>javac -cp npub1 cpmain1.java

因指定classpath而找到cpsub1.class,並將資料夾js1cpmain1.java編譯至資料夾js1cpmain1.class

 

 圖25-15 

 [範例-錯誤]

C:\js1>java cpmain1

因沒指定cpsub1.class所在資料夾,故找不到cpsub1.class,發生下述錯誤。

 

 圖25-16 

Exception in thread "main" java.lang.NoClassDefFoundError: cpsub1

        at cpmain1.main(cpmain1.java:3)

Caused by: java.lang.ClassNotFoundException: cpsub1

        at java.net.URLClassLoader$1.run(URLClassLoader.java:372)

        at java.net.URLClassLoader$1.run(URLClassLoader.java:361)

        at java.security.AccessController.doPrivileged(Native Method)

        at java.net.URLClassLoader.findClass(URLClassLoader.java:360)

        at java.lang.ClassLoader.loadClass(ClassLoader.java:424)

        at sun.misc.Launcher$AppClassLoader.loadClass(Launcher.java:308)

        at java.lang.ClassLoader.loadClass(ClassLoader.java:357)

        ... 1 more

 

[範例-錯誤]

C:\js1>java -cp npub1 cpmain1

錯誤: 找不到或無法載入主要類別 cpmain1

-cp只指定cpsub1.java所在資料夾,故發生上述錯誤。

 

[範例-相對路徑]

C:\js1>java -cp .;npub1 cpmain1

a = 10

-cp指定.(現行資料夾,存放cpmain1.class)npub1(cpsub1.class存放資料夾)即可執行。

 

[範例-絕對路徑]

C:\js1>java -cp C:\js1;C:\js1\npub1 cpmain1

a = 10

指定絕對路徑亦同。

 

 

[25-3 SOURCEPATH]

為編譯程式javac使用之命令列指令選項引數。指定原始程式碼編譯(javac指令)的原始檔(.java)輸入來源資料夾。

 

命令列指令選項引數:sourcepath(前置-)

變數值:自定

適用時機為javac編譯source code(.java)之輸入路徑。

 

 圖25-17各環境變數、引數關係圖(SOURCEPATH)  

 

[25-3-1 SOURCEPATH設定方式]

[命令列選項引數]

使用命令列選項引數-sourcepath設定原始碼檔資料夾,可設定多個值,以;(分號)區隔,搜尋時會依序尋找,使用第一個找到者。有效期間為該次執行之javac指令,下次執行時須於javac指令再指定該選項引數。

指定格式:javac -sourcepath 資料夾所屬資料夾\主類別名稱.java

指定例:C:\js1>javac -sourcepath npub1 npub1\Main22

注意:須加入所屬資料夾。

資料夾指定格式可分為相對位置及絕對位置,如目前資料夾為C:\js1

相對位置:C:\js1>javac -sourcepath npub1 npub1\Main22

絕對位置:C:\js1>javac -sourcepath C:\js1\npub1 npub1\Main22

 

圖25-18 SOURCEPATH範例目錄結構   

 [25-3-2 SOURCEPATH的選擇原則]

 

圖25-19 SOURCEPATH的選擇原則  

 

 

編譯/執行時原始碼檔及位元碼檔資料夾之關聯如下二表:

 

25-1 單一類別檔案

 

單一/複數

類別檔

一般類別/

主類別

一般類別

資料夾

主類別

資料夾

一般及主類別資料夾

sourcepath

指定

編譯執行

時資料夾

.java來源

資料夾

單一  

一般類別

A

 

 

 

A

A

單一  

主類別

 

A

 

 

A

A

單一  

一般類別

B

 

 

 

A

編譯錯誤

單一  

主類別

 

B

 

 

A

編譯錯誤

單一  

一般類別

A

 

 

B

A

編譯錯誤

單一  

主類別

 

A

 

B

A

編譯錯誤

單一  

一般類別

B

 

 

B

A

B

單一  

主類別

 

B

 

B

A

B

單一  

一般+

 

 

A

 

A

A

單一  

一般+

 

 

A

B

A

編譯錯誤

單一  

一般+

 

 

B

B

A

B

 

 

 

 

25-2 複數類別檔案-一般類別、主類別各成單一檔案,主類別會實作一般類別

 

單一/複數

類別檔

一般類別/

主類別

一般類別

資料夾

主類別

資料夾

一般類別

.class

sourcepath

指定

編譯執行

時資料夾

.java來源

資料夾

複數

一般類別

A

 

A

 

A

A

主類別

 

A

 

複數

一般類別

B

 

 

 

A

編譯錯誤

主類別

 

 

 

複數

一般類別

B

 

 

B

A

編譯錯誤

主類別

 

A

 

複數

一般類別

B

 

 

A;B

A

B

主類別

 

A

 

A

複數

一般類別

B

 

 

B

A

B

主類別

 

B

 

 

上述表格僅為部分舉例。

紅字為二者有存在其一,或兩者皆存在。

主類別編譯時,一般類別的.class檔或.java檔所在之資料夾須指定正確。

 

[範例原始檔內容]

.java檔:class_m5.java

class class_a5 {  int x = 20;  }

class class_m5{

  public static void main(String[] args){

    class_a5 obj1 = new class_a5 ();

    obj1.x = obj1.x + 5;

    System.out.println("x的值為" + obj1.x);  } }

 

.java檔:class_m6.java

class class_a6 {  int x = 20;  }

class class_m6{

  public static void main(String[] args){

    class_a6 obj1 = new class_a6 ();

    obj1.x = obj1.x + 6;

    System.out.println("x的值為" + obj1.x);  } }

 

.java檔:class_m7.java

class class_a7 {  int x = 20;  }

class class_m7{

  public static void main(String[] args){

    class_a7 obj1 = new class_a7 ();

    obj1.x = obj1.x + 7;

    System.out.println("x的值為" + obj1.x);  } }

 

[sourcepath選項引數設定時,適用執行時資料夾]

.java檔:class_m5.java

存放資料夾:C:\js1

執行時資料夾:C:\js1

 

 圖25-20 無sourcepath選項引數  

 

[範例]

C:\js1>javac class_m5.java

C:\js1>java class_m5

x的值為25

   

[sourcepath 設定C:\js1\npub1,適用該資料夾]

.java檔:class_m6.java

存放資料夾:C:\js1\npub1

執行時資料夾:C:\js1

 

 圖25-21 指定sourcepath選項引數  

 

[相對路徑]                                                

C:\js1>javac -sourcepath npub1 class_m6.java

javac: file not found: class_m6.java

Usage: javac <options> <source files>

use -help for a list of possible options

class_m6.java前沒加上資料夾名稱

 

C:\js1>javac -sourcepath npub1 npub1\class_m6.java

C:\js1>java -cp npub1 class_m6

x的值為26

 

[絕對路徑]

C:\js1>javac -sourcepath C:\js1\npub1 npub1\class_m6.java

C:\js1>javac -sourcepath C:\js1\npub1 C:\js1\npub1\class_m6.java

C:\js1>java -cp npub1 class_m6

x的值為26

 

[原始檔和位元檔分開存放]

原始檔(.java)和位元檔(.class)混在同一資料夾較難管理,一般將其分別存放在不同之資料夾裡。

[sourcepath 設定C:\js1\npub1-d設定C:\ctcsource1]

.java檔:class_m6.java

原始檔存放資料夾:C:\js1\npub1

位元檔存放資料夾:C:\ctcsource1

執行時資料夾:C:\js1

 

[執行例]                                                

C:\js1>javac -sourcepath npub1 -d C:\ctcsource1 npub1\class_m7.java

C:\js1>java -cp C:\ctcsource1 class_m7

x的值為27

 

圖25-22 原始檔和位元檔分開存放  

arrow
arrow

    祈泊 發表在 痞客邦 留言(0) 人氣()