隨著 JEP 511: Module Import Declarations 和 JEP 512: Compact Source Files and Instance Main Methods 正式納入 Java,Java 25 的寫法有了革命性變化,可以用結構化程式設計的手法,隨手寫些小型程式。搭配 Java 22 的 JEP 458: Launch Multi-File Source-Code Programs,不用編譯就能直接執行 *.java,更是絕妙~
為了慶祝 Java 迎來新的程式寫法,我寫了幾個範例來示範它的好處!
程式碼需要 OpenJDK JDK 25 Early-Access Build 22 或更新的版號,才能編譯與執行,請至 https://jdk.java.net/25/ 下載。
然而,好處只顯現在隨手寫「只有一個 *.java 檔案」的小型程式,因為它的壞處是整個程式都是基於 static 的變數和函式(所以很有程序導向的風格),因此這不是取代原先物件導向寫法用的,更不是萬靈丹,稍具規模的複雜程式碼,還是要寫成 class 再 new 一堆物件來用,才是最佳解!但反過來,如果我們的 Java 應用程式只由 main() 構成,單純調用現成的 API 功能來組合成一個程式,那 JEP 512 是最佳解,沒必要為此寫個 class 來 new~
這是最簡單的例子,用 Properties 讀寫檔案資料,來示範 Java 25 新的寫法。
用序列化另一個類別的例子,示範 Java 25 在 main() 以外弄個 class 來用的情形。
用 Socket 的 server 和 client,示範啟動兩個都是 Compact Source Files and Instance Main Methods 的情形。
先執行 server.bat,再執行 client.bat。
用 Java 25 寫一個 GET 的 HTTP 後端程式,埠號 32768。並且啟動 Java 18 起自帶的網頁伺服器(jwebserver.exe),埠號 80。
這範例單靠 OpenJDK 25,免安裝任何伺服器,就能架個後端系統,讓前端 HTML5 調用,藉由 Java 做一些前端做不到的事情。
startup.bat 用來啟動程式,client.lnk(捷徑)用來連線到 http://127.0.0.1,你也可以直接打開瀏覽器輸入。
這是個刻意複雜化、把事情做過頭的範例,如果你對 GUI 沒興趣,那沒必要理會本範例,直接跳過,不影響本專題!
這範例將 Swing 重新包裝成去 J 開頭的 API,也就是 libgui.java,用它來打造 GUI 應用程式,以此示範 Java 25 在 main() 以外調用程式庫,並統一打包成一個 package.jar 來使用的情形。
差別在過去總是把 libgui.java 編譯成 *.class 類別檔,再給其他專案下 -classpath 參數使用,而程序導向風格是直接把原始碼複製到想用它的專案底下,同時編譯,一起打包到執行檔裡。
這是因為程序導向風格的程式設計手法,實作細節也很重要!所以不是給封裝過的類別,而是給原始碼,藉由檢視每個函式的實作細節來釐清問題,而不是只給編譯過的套件。所以刻意寫了這樣一個範例,用來檢視在 Java 25 的「隨手用來寫些小型程式」風格下,只給原始碼而不給類別檔,是好還是不好?這沒有標準答案,我覺得好,才會寫出這樣的程式,而你喜歡下 -classpath 參數掛載 *.class 和 *.jar 也是很好的風格。
這範例順便示範 Java 的 GUI 應用程式,即使不使用 Executable JAR 格式,也能在沒有命令提示字元視窗下啟動,第一種做法是 run.bat,簡單、直覺,缺點是依然會瞬閃一個命令提示字元視窗,一個是更好的做法 run.lnk(捷徑),新增捷徑,輸入 %JAVA_HOME%\bin\javaw.exe -cp .;* main,建立捷徑後,把捷徑的「開始位置」清空,或指向這個 Java 應用程式的資料夾,這樣應用程式用相對路徑存取檔案的話才找得到。