




版權(quán)說明:本文檔由用戶提供并上傳,收益歸屬內(nèi)容提供方,若內(nèi)容存在侵權(quán),請進(jìn)行舉報(bào)或認(rèn)領(lǐng)
文檔簡介
Java
虛擬機(jī)基礎(chǔ)教程
目錄
第1章Java虛擬機(jī)
1.1JVM實(shí)現(xiàn)
1.2為何要在JVM上開發(fā)
1.2.1JVM適應(yīng)市場的變化
1.2.2Java類庫
1.2.3生態(tài)系統(tǒng)
1.3常見的用途
1.3.1Web應(yīng)用程序
1.3.2大數(shù)據(jù)
1.3.3IoT
1.4JVM概念
1.4.1虛擬機(jī)
1.4.2JIT編譯器
1.4.3基本數(shù)據(jù)類型
1.4.4類
1.4.5引用類型
1.4.6垃圾收集器
1.4.7向后兼容
1.4.8構(gòu)建工具
1.5Java版本
1.5.1JavaSE
1.5.2JavaEE
1.5.3JavaME
1.6其他JVM語言
1.6.1為何選擇其他語言
1.6.2在同一個(gè)項(xiàng)目中使用多種JVM語言
1.6.3使用另一種語言編寫單元測試
1.7小結(jié)
第2章Java虛擬機(jī)開發(fā)
2.1JDK
2.1.1安裝JDK
2.1.2探索JDK
2.1.3JRE
2.2使用包組織類
2.2.1包是什么
2.2.2選擇包名
2.2.3包名舉例
2.2.4全限定類名
2.3Java類庫
2.3.1Java類庫的組織結(jié)構(gòu)
2.3.2包概述
2.3.3java,lang包中的重要類
2.3.4集合APIjava.util.ArrayList和java.util.HashMap
2.4從命令行運(yùn)行JVM應(yīng)用程序
2.4.1至少有一個(gè)類包含靜態(tài)方法main。
2.4.2存儲類文件的Fl錄結(jié)構(gòu)
2.4.3為JVM實(shí)例設(shè)置ClassPath
2.4.4將類文件放在JAR歸檔文件中
2.4.5使用命令java運(yùn)行程序
2.4.6在JVM中運(yùn)行的示例項(xiàng)目
2.5EelipseIDE
2.5.1下載EclipseIDE
2.5.2安裝EclipseIDE
2.6小結(jié)
第3章Java
3.1Java中的面向?qū)ο缶幊坦δ?/p>
3.1.1定義類
3.1.2類訪問限定符
3.1.3類限定符final——鎖定類
3.1.4定義包
3.1.5導(dǎo)入類
3.1.6添加類成員變量和方法
3.1.7限定符
3.1.8構(gòu)造函數(shù)和終結(jié)方法
3.1.9向上轉(zhuǎn)換和向下轉(zhuǎn)換
3.2編寫Java代碼
3.2.1運(yùn)算符
3.2.2條件檢查
3.2.3POJO
3.2.4數(shù)組
3.2.5泛型
環(huán)
循
3.2.6
常
異
3.2.7
程
線
3.2.8
3.2.91ambda
3.3編程風(fēng)格指南
3.4小測驗(yàn)
3.5小結(jié)
第4章Java編程
4.1配置EclipseIDE
4.2使用Java創(chuàng)建Web服務(wù)
4.2.1在EclipseIDE中新建Gradle項(xiàng)目
4.2.2修改Gradle構(gòu)建文件
4.2.3構(gòu)建項(xiàng)目
4.2.4編寫后端類
4.3小結(jié)
第5章Scala
5.1安裝Scala
5.2Scala的REPLshell
5.3函數(shù)式編程和命令式編程
5.4Scala語法和規(guī)則
541靜本舉型語言
5.4.2可修寶的變量和不可修改的變量
5.4.3常用的Scala類型
5.5Scala的OOP功能
5.5.1定義包和子包
5.5.2導(dǎo)入成員
5.5.3定義類
5.5.4實(shí)例變量和實(shí)例方法
5.5.5構(gòu)造函數(shù)
5.5.6擴(kuò)展類
5.5.7重載方法
5.5.8抽象類
5.5.9特質(zhì)
5.5.10單例對象
5.5.11運(yùn)算符重載
5.5.12Case類
5.6Scala標(biāo)準(zhǔn)庫
5.6.1泛型
5.6.2集合
5.6.3XML處理
5.7Scala的函數(shù)式編程功能
5.7.1使用函數(shù)遍歷集合
5.7.2映射-過濾-歸約設(shè)計(jì)模式
5.7.3柯里化
5.8小測驗(yàn)
5.9小結(jié)
第6章Scala編程
6.1ScalaIDEforEclipse插件
6.1.1安裝ScalaIDEforEclipse
6.1.2切換到ScalaIDE透視圖
6.2SBT
6.2.1安裝SBT
6.2.2創(chuàng)建基于SBT的EclipseIDE項(xiàng)目
6.2.3Scala編譯器(scalac)
6.3創(chuàng)建Akka項(xiàng)目
6.3.1在SBT構(gòu)建文件中添加Akka依賴項(xiàng)
6.3.2更新ScalaIDE項(xiàng)目
6.3.3Akka概念
6.3.4創(chuàng)建第一個(gè)AkkaActorQuotesHandlerActor
6.3.5創(chuàng)建消息
6.3.6編寫基于ScalaTest的單元測試
6.3.7實(shí)現(xiàn)消息處理程序
6.3.8創(chuàng)建QuotePrinterActor
6.3.9主應(yīng)用程序
6.4小結(jié)
第7章Clojure
7.1安裝Clojure
創(chuàng)建啟動腳本
7.2Clojure的交互式shell(REPL)
7.3Clojure語言
7.3.1語法
7.3.2表達(dá)式
7.3.3定義變量
7.3.4定義函數(shù)
7.3.5數(shù)據(jù)結(jié)構(gòu)
7.4使用Java類
使用deftype和defrecord創(chuàng)建簡單的Java類
7.5使用代理管理狀態(tài)
代理示例
7.6風(fēng)格指南
7.7小測驗(yàn)
7.8小結(jié)
第8章Clojuro編程
8.1EclipseIDE插件Counterclockwise
8.1.1安裝插件Counterclockwise
8.1.2切換到Java透視圖
8.2構(gòu)建工具Leiningen
安裝Leiningen
8.3創(chuàng)建可執(zhí)行的Clojure程序
8.3.1在不使用Leiningen的情況下將代碼編譯成類文件
8.3.2使用Leiningen編譯項(xiàng)目
8.4新建Counterclockwise項(xiàng)目
8.4.1EclipseIDE中的ClojureREPL
8.4.2更新項(xiàng)目的Clojure版本
8.4.3添加依賴
8.5以測試驅(qū)動開發(fā)的方式探索monad
8.6Web框架Luminus
8.6.1創(chuàng)建Luminus項(xiàng)目
8.6.2將項(xiàng)目導(dǎo)入Counterclockwise
8.6.3探索Luminus項(xiàng)目
8.6.4在Web應(yīng)用程序中添加頁面
8.7小結(jié)
第9章Kot1in
9.1安裝Kotlin
啟動腳本
9.2Kot1in的REPL交互式shell
9.3Kotlin語言基礎(chǔ)
9.3.1定義局部變量
9.3.2定義函數(shù)
9.3.3Kotlin類型
9.3.4循環(huán)
9.4Kotlin的OOP功能
9.4.1定義包
9.4.2導(dǎo)入成員
9.4.3定義類和構(gòu)造函數(shù)
9.4.4給類添加成員
9.4.5繼承
9.4.6接口
9.4.7可見性限定符
9.4.8單例對象和伴生對象
9.4.9數(shù)據(jù)類
9.4.10lambda和內(nèi)聯(lián)函數(shù)
9.5Kotlin過程性編程
9.6風(fēng)格指南
9.7小測驗(yàn)
9.8小結(jié)
第10章Kotlin編程
10.1EclipseIDEKotlin插件
10.1.1安裝EclipseIDEKotlin插件
10.1.2切換到Kotlin透視圖
10.2ApacheMaven
10.2.1安裝ApacheMaven
10.2.2下載預(yù)制的Kotlin基本套件
10.2.3在EclipseIDE中導(dǎo)入項(xiàng)目
10.2.4探索構(gòu)建文件pom.xml
10.2.5在Eelipse中更新構(gòu)建文件
10.3創(chuàng)建JavaFX桌面GUI應(yīng)用程序
10.3.1定制項(xiàng)目
10.3.2創(chuàng)建可運(yùn)行的應(yīng)用程序
10.3.3編寫擴(kuò)展函數(shù)
10.3.4布局窗格
10.3.5實(shí)現(xiàn)基干BordorPane的布局
10.3.6實(shí)現(xiàn)動畫
10.3.7調(diào)試程序
10.4小結(jié)
第II章Groovy
11.1安裝Groovy
GroovyConsole和GroovyShell
11.2Groovy語言
Groovy面向?qū)ο缶幊?/p>
11.3Groovy開發(fā)包(GDK)
11.3.1Groovy字符串(GString)
11.3.2集合
11.4動態(tài)和靜態(tài)編程
11.4.1元編程
11.4.2Groovy靜態(tài)編程
11.5小測驗(yàn)
11.6小結(jié)
第12章Groovy編程
12.1安裝GroovyEclipse插件
切換到Java透視圖
12.2ApacheIvy和IvyDE
安裝用于EclipseIDE的ApacheIvyDE插件
12.3創(chuàng)建并配置項(xiàng)目
12.3.1新建GroovyEclipse項(xiàng)目
12.3.2創(chuàng)建供Ivy使用的ivy.xml文件
12.4JavaDatabaseConnectivity(JDBC)
12.4.1H2數(shù)據(jù)庫
12.4.2創(chuàng)建內(nèi)存數(shù)據(jù)庫
12.5使用MarkupBuilder生成XML
根據(jù)SQL查詢結(jié)果生成XML
12.6微服務(wù)平臺Vert,x
12.6.1在文件ivy.xml中添加Vert.x依賴
12.6.2創(chuàng)建Web服務(wù)
12.7小結(jié)
附錄A其他JVM語言
A.1OracleNashorn
A.1.1在基于JVM的項(xiàng)目中嵌入Nashorn
A.1.2運(yùn)行Nashorn
A.2Jython(Python)
A.2.1CPython和Jython的不同之處
A.2.2運(yùn)行Jython
A.3JRuby(Ruby)
A.3.1RubyonRails和JRuby
A.3.2運(yùn)行JRuby
A.4Frege(Haskel1)
A.4.1在Frege中調(diào)用Java代碼
A.4.2運(yùn)行Frege
A.5Ceylon
A.5.1Ceylon的模塊系統(tǒng)
A.5.2運(yùn)行Ceylon
A.6小結(jié)
附錄B小測驗(yàn)答案
第1章Java虛擬機(jī)
Java虛擬機(jī)(JavaVirtualMachine,JVM)是一個(gè)可用于開發(fā)和部署軟件的現(xiàn)代平臺。顧名
思義,最初開發(fā)它旨在支持使用Java語言編寫的應(yīng)用程序,但設(shè)計(jì)Java的人不久就認(rèn)識到,
JV.M不僅可運(yùn)行Java語言,還可利用Java的功能和龐大的類庫。
1995年,Sun公司1發(fā)布了Java和第一個(gè)JVM實(shí)現(xiàn)。鑒于其重點(diǎn)是網(wǎng)絡(luò)應(yīng)用程序,Java很快
就大行其道;它還被設(shè)計(jì)成可隨處運(yùn)行。開發(fā)Java的初衷是用于機(jī)頂盒編程,但Sun公司發(fā)
現(xiàn)彼時(shí)機(jī)頂盒市場還不成熟,因此決定同時(shí)將這個(gè)平臺推向臺式機(jī)。為此,Sun公司設(shè)計(jì)了一
種獨(dú)特的二進(jìn)制可執(zhí)行格式,并稱之為Java字節(jié)碼。要運(yùn)行被編譯成Java字節(jié)碼的程序,系
統(tǒng)必須安裝JVM實(shí)現(xiàn)。
iSun公司于2009年4月被Oraele公司收購。一一編者注
本書將簡要地介紹5種最流行的JVM語言。通過學(xué)習(xí)這些語言的基礎(chǔ)知識,并動手編寫代碼,
你將能夠做出判斷,確定哪種語言對你、你的團(tuán)隊(duì)和項(xiàng)目來說是最合適的。
我們先來說點(diǎn)實(shí)在的,到第2章再深入介紹Java開發(fā)包(JDE)和Java類庫,當(dāng)前,可使用
的編程語言和平臺眾多,它們相互爭奪市場,因此有必要先來詳細(xì)地說說JVM向開發(fā)人員提供
了什么。有鑒于此,本章將介紹如下主題:
?為何要在JVM上進(jìn)行開發(fā);
?JVM的常見用途;
?JVM概念簡介;
?Java版本;
?其他JYM語言。
1.1JVM實(shí)現(xiàn)
需要指出的是,本書只考慮與OracleJavaSE8(和更高版本)兼容的實(shí)現(xiàn)。這個(gè)版本
可在臺式機(jī)、服務(wù)器和眾多單板計(jì)算機(jī)(包括尺寸如信用卡的所有RaspberryPi)上安裝。
本書使用的是Oracle的JVM實(shí)現(xiàn),你也可使用開源的OpenJDK和IBM的J9JavaSE實(shí)現(xiàn)。
本書不涵蓋Google發(fā)布的用于Android手機(jī)和平板電腦的Java平臺,因?yàn)橛糜贏ndroid的
Java版本基于較舊的Java版本。雖然用于Android的Java平臺版本越來越新,但它并未提
供Orac"JavaSE8的所有功能,且需要使用不同的編譯器和工具八另外,Gccgla刪除了大
量的JavaSEAPI,取而代之的是Google自己開發(fā)的不兼容的API。然而,本書介紹的有些語
言也可用于Android開發(fā)。例如,Kotlin就是一種非常流行的Android開發(fā)語言,但本書不
會龍此展開討論。
1.2為何要在JVM上開發(fā)
當(dāng)前,可供使用的編程語言和平臺眾多,為何要在JVM上開發(fā)和部署項(xiàng)目呢?因?yàn)镴VM最初是
為Java語言開發(fā)的,而近年來,其他語言的擁是無數(shù)次地宣稱,Java語言已過時(shí)乃至死亡。
近年來,流行的編程語言如走馬燈似的更換,而Java猶如常青樹,始終處于全球使用最多的
編程語言排行榜的前列。
JVM平臺為何如此強(qiáng)大呢?下面來看看其中一些最重要的原囚:
?它適應(yīng)市場的變化,從而確保與時(shí)俱進(jìn):
?內(nèi)置的Java類庫非常強(qiáng)大;
?它有無可比擬的生態(tài)系統(tǒng)。
1.2.1JVM適應(yīng)市場的變化
Java于20世紀(jì)90年代中期面世,那時(shí)的計(jì)算機(jī)裝備的都是單核CPU,內(nèi)存量也沒有兒個(gè)GB,
因?yàn)閮?nèi)存條貴得不得了。Java是與時(shí)俱進(jìn)的語言之一:多核CPU面世后不久,Java就通過在
多個(gè)線程中運(yùn)行代碼來支持多核,但它并沒有就此止步,而是在每次推出新版本時(shí),都添加了
讓并發(fā)編程更容易的新類。這種做法到現(xiàn)在依然沒有停止。
函數(shù)式編程范式大行其道后,Java在核心語言中新增了對1alibda和流的支持。雖然Java提
供這種支持的時(shí)間很晚,但相比于其他流行的語言,其實(shí)現(xiàn)更佳。這是因?yàn)槌绦騿T幾乎什么都
不用做就能實(shí)現(xiàn)多線程。
適應(yīng)市場變化還意味著有時(shí)需要做減法。Java面世時(shí),熱點(diǎn)是直接在瀏覽器中運(yùn)行Java代碼。
這些微型程序被稱為applet,要求瀏覽器和系統(tǒng)安裝專用的瀏覽器插件。而現(xiàn)在,市場已將
JavaScript作為創(chuàng)建交互式網(wǎng)站的標(biāo)準(zhǔn)語言。有鑒于此,Oracle最近摒棄了aDDlet標(biāo)準(zhǔn)。
1.2.2Java類庫
在每個(gè)Java版本(這將在本章后面更詳細(xì)地介紹)中,都指定了相應(yīng)的JVM實(shí)現(xiàn)必須提供哪
些類。JavaSE8的類庫包含大量的類,每個(gè)遵循JavaSE8平臺標(biāo)準(zhǔn)的JVM實(shí)現(xiàn)都必須實(shí)現(xiàn)
這些類,而不管這種實(shí)現(xiàn)是由誰開發(fā)的。
這個(gè)類庫中的類提供了諸如讀寫控制臺窗口、執(zhí)行文件I/O以及與TCP服務(wù)器進(jìn)行通信等功能,
還有很多用于啟動和管理操作系統(tǒng)線程的類。更重要的是,還包含定義列表和映射(在有些語
言中稱為字典)等眾多數(shù)據(jù)結(jié)構(gòu)的類。下一章將詳細(xì)介紹Java類庫中的類。
Java類庫是語言設(shè)計(jì)人員將JVM作為目標(biāo)開發(fā)平臺的重要原因之一。有了這個(gè)類庫定義的數(shù)
據(jù)結(jié)構(gòu)后,他們能夠史專注于語言設(shè)計(jì),而不用太專注于從頭開始打造完整的運(yùn)行時(shí)庫。要知
道,打造能夠與Java類庫媲美的、經(jīng)過全面測試的、多平臺運(yùn)行時(shí)系統(tǒng)類庫可是一項(xiàng)艱巨的
任務(wù)。
1.2.3生態(tài)系統(tǒng)
顯然,內(nèi)置的類庫不可能涵蓋程序員的所有用例。對于內(nèi)置類庫缺失的東西,可求助于其他公
司、組織和個(gè)人開發(fā)的庫和工具,以節(jié)省開發(fā)時(shí)間。鑒于很多年來Java都非常成功,其生態(tài)
系統(tǒng)是無可比擬的,因此很難找到一個(gè)這樣的平臺,即其中可供選擇的工具、庫、工具包和框
架比JVM提供的還要好。
鑒于可供使用的插件庫眾多,開發(fā)人員的開發(fā)方向幾乎不會受到Java的限制。為說明Java
生態(tài)系統(tǒng)有多豐富,我們來看看創(chuàng)建Web應(yīng)用程序時(shí),Java開發(fā)人員通常具有的選擇空間:
?創(chuàng)建在JVM應(yīng)用程序服務(wù)器中運(yùn)行的Web應(yīng)用程序;
?為快速獲得結(jié)果,可使用通用的高級Web框架;
?為獲得更大的控制權(quán),可使用微服務(wù)框架來創(chuàng)建應(yīng)用程序。
場景L使用JVM應(yīng)用程序服務(wù)器
開發(fā)人員可以像企業(yè)那樣安裝基于JV'M的應(yīng)用程序服務(wù)器(這可以是開源的,也可以是付費(fèi)的
專用服務(wù)器),并使用它來運(yùn)行應(yīng)用程序和Wob應(yīng)用程序。這種服務(wù)器將負(fù)責(zé)處理配置問題以
及管理數(shù)據(jù)庫連接。
有簡單的應(yīng)用程序服務(wù)器,它們只包含運(yùn)行基本W(wǎng)eb應(yīng)用程序所需的內(nèi)置API。但也有經(jīng)過
Oracle認(rèn)證的功能齊備的應(yīng)用程序服務(wù)器,它們提供了大量內(nèi)置的標(biāo)準(zhǔn)化API,其中包括訪問
數(shù)據(jù)庫的API、生成或使用XML和JSON文檔的API、按SOAP或REST標(biāo)準(zhǔn)與其他Web服務(wù)通信
的API、確保Web安全的API、向遺留計(jì)算機(jī)系統(tǒng)發(fā)送消息或從這些系統(tǒng)接收消息的API等。
下面是兩個(gè)最重要的企業(yè)開發(fā)框架:
?OracleJava企業(yè)版(JavaEE)平臺,這將在本書后面介紹;
?Spring框架生態(tài)系統(tǒng)(其中包括SpringBoot)<,
很多應(yīng)用程序都結(jié)合使用了這兩種技術(shù)。
下面是一些流行的應(yīng)用程序服務(wù)器:
?ApacheTomcat(用于運(yùn)行簡單的Web應(yīng)用程序);
?ApacheTomEE:
?RedHatWildFly;
?OracleGlassFish;
?RedHatJBossEnterpriseApplicationPlatform;
?OracleWebLogico
其中前四個(gè)是開源的,而后兩個(gè)是專用的。
場景2:使用高級的通用Web應(yīng)用程序框架
第二種選擇是使用完整的Web應(yīng)用程序框架。相比于企業(yè)框架,這些框架提供的API通常更高
級,它們還提供了內(nèi)置的模型-視圖-控制器(model-view-controller,MVC)解決方案,可極
大地提高開發(fā)人員的效率。
使用這些框架時(shí),開發(fā)人員的選擇通常受到限制,因?yàn)樗鼈冎恢С譃閿?shù)不多的幾個(gè)庫和工具包。
然而,它們支持添加插件來提供其他選擇。換而言之,使用這些框架是以放棄一些選擇空間來
換取更短的開發(fā)周期。有些框架要求應(yīng)用程序運(yùn)行在JVM應(yīng)用程序服務(wù)器中,而有些提供了自
己的HTTP服務(wù)器。
在這種框架中,ApacheStruts一度非常流行,但現(xiàn)在最流行的可能是Play。
場景3:使用微服務(wù)框架
另一種選擇是使用現(xiàn)代微服務(wù)框架來創(chuàng)建應(yīng)用程序。這些框架提供了內(nèi)置的HTTP服務(wù)器,可
用于運(yùn)行應(yīng)用程序,但沒有提供其他任何現(xiàn)成的工具和庫。在這種情況下,更容易根據(jù)需要混
合使用不同的庫和工具包。
為了采用現(xiàn)代微服務(wù)架構(gòu),通常將應(yīng)用程序分成多個(gè)獨(dú)立的Web服務(wù),但這些框架并不要求你
必須這樣做。
最常用的微服務(wù)框架包括Vert,x和SparkJava,其中后者并非是用于ApacheSpark大數(shù)據(jù)
平臺的。
1.3常見的用途
前面提供了一些證據(jù),證明了JVV是切實(shí)可行的現(xiàn)代軟件開發(fā)平臺,下面來看看一些常見的
JVM用途:
?呢b應(yīng)用程序;
?大數(shù)據(jù)分析;
?物聯(lián)網(wǎng)。
1.3.1Web應(yīng)用程序
非常重視性能,很多人都選擇使用它來開發(fā)Wob應(yīng)用程序。在設(shè)計(jì)正確的情況下,應(yīng)用程
序在需要跨越眾多不同服務(wù)器時(shí)的伸縮性極佳。
JV'I是一個(gè)大家了解得非常清楚的平臺,這意味著其行為是可預(yù)測的。另外,它還提供了很多
T具.可用來調(diào)試和剖析有問題的應(yīng)用程序°鑒于JVM是開源的,完全可以對其內(nèi)部進(jìn)行監(jiān)視.
對那些必須同時(shí)為數(shù)以千計(jì)的用戶提供服務(wù)的Web應(yīng)用程序來說,這是一個(gè)非常重要的優(yōu)點(diǎn)。
JVV在云計(jì)算中扮演著重要的角色。Twitter>Amazon、Spotify和Netflix等很多著名公司都
在其基于云的服務(wù)的核心部分使用了JVNU
1.3.2大數(shù)據(jù)
大數(shù)據(jù)是當(dāng)前的一個(gè)熱點(diǎn)。在數(shù)據(jù)太大,尢法使用傳統(tǒng)的數(shù)據(jù)庫進(jìn)行分析時(shí),可搭建多個(gè)數(shù)據(jù)
庫集群來處理它們。大數(shù)據(jù)分析包括查找特定的信息、找出規(guī)律、計(jì)算統(tǒng)計(jì)指標(biāo)等。
這種數(shù)據(jù)可能是從Web服務(wù)器收集的數(shù)據(jù)(如已登錄用戶的單擊)、位于制造車間的外部傳感
器的輸出、遺留服務(wù)器多年來生成的日志文件等。它們的規(guī)模各不相同,但通常多達(dá)數(shù)TB。
下面是大數(shù)據(jù)領(lǐng)域兩種流行的數(shù)據(jù)分析技術(shù)。
?ApacheHadoop:負(fù)責(zé)存儲數(shù)據(jù)以及將數(shù)據(jù)分發(fā)到其他服務(wù)器。
?ApacheSpark:使用Hadoop對數(shù)據(jù)進(jìn)行流化(stream),以便能夠?qū)Φ絹淼臄?shù)據(jù)進(jìn)行分
析。
Hadoop和Spark都主要是使用Java編寫的。它們都提供了接口,以支持大量的編程語言和平
臺,其中當(dāng)然包括jVMo
函或式編程蔡式致力于。創(chuàng)建可在多個(gè)CPU內(nèi)核中安全運(yùn)行的代碼,因此進(jìn)行Spark或Hadoop
編程時(shí),Scala和Clojure等純函數(shù)式編程語言是非常合適的選擇。
1.3.3IoT
當(dāng)前,能夠連接到Internet的移動設(shè)備非常普及。鑒于Java最初就是為在嵌入式設(shè)備中運(yùn)行
而設(shè)計(jì)的,因此在IoT領(lǐng)域,JVM也處于優(yōu)勢地位。
對于內(nèi)存有限的系統(tǒng),Oracle提供了JavaMEEmbedded平臺。這種平臺是專門為不需要標(biāo)準(zhǔn)
圖形(或基于控制臺的)用戶界面的商用IoT設(shè)備設(shè)計(jì)的。
對于那些內(nèi)存還算寬裕的設(shè)備,可使用JavaSEEmbedded版。JavaSEEmbedded與本書討論
的JavaSE很像,在運(yùn)行完整Linux的環(huán)境中,可使用它來提供桌面GUI,以支持全面的用戶
交互。
JavaMEEmbedded和JavaSEEmbedded平臺都能夠訪問RaspberryPi的通用輸入/輸出
(general-purposeinput/output,GP10)針腳,這意味著可通過Java代碼來訪問這些端口
連接的傳感器和其他外圍設(shè)備。
1.4JVM概念
要有所作為,JVM開發(fā)人員必須熟悉下面這些最重要的JVM概念:
?JVM是一種虛擬機(jī):
?JVM實(shí)現(xiàn)大都自帶即時(shí)(just-in-time,J1T)編譯器;
?JVM提供了一些內(nèi)置的基本類型;
?除基本類型之外的其他一切都是對象;
?對象是通過引用類型來訪問的;
?垃圾收集器(garbagecollector,GO進(jìn)程將過期的對象從內(nèi)存中刪除;
?JVM大量地使用構(gòu)建工具。
1.4.1虛擬機(jī)
Java虛擬機(jī)是一種虛擬機(jī),這一點(diǎn)顯而易見,但必須牢記在心。這意味著從理論上說,在一
種計(jì)算機(jī)上開發(fā)的應(yīng)用程序,可在另一種計(jì)算機(jī)上運(yùn)行。
一般而言,代碼在32位壞是64位的Java運(yùn)行時(shí)環(huán)境(JavaRuntimeEnvironment.JRE)U」
運(yùn)行無關(guān)緊要。在64位的運(yùn)行時(shí)環(huán)境中運(yùn)行時(shí),應(yīng)用程序可使用的內(nèi)存可能更多,但只要應(yīng)
用程序不執(zhí)行原生操作系統(tǒng)調(diào)用或需要數(shù)GB的內(nèi)存,這種差別就無關(guān)緊要。
在C等語言中,數(shù)據(jù)類型的長度取決于原生系統(tǒng),而Java不存在這樣的問題或特色(這
是問題還是特色取決于你怎么看)。在JVM中,整型都是無符號的且長32位,而不管運(yùn)行程
序的是哪種計(jì)算機(jī)平臺或系統(tǒng)架構(gòu)。
最后,需要指出的是,在JVM中運(yùn)行的每個(gè)應(yīng)用程序都在系統(tǒng)內(nèi)存中加載自己的JV”實(shí)例。這
意味著同時(shí)運(yùn)行多個(gè)Java應(yīng)用程序時(shí),每個(gè)應(yīng)用程序都有自己的JVM副本;這還意味著在必
要的情況下,不同的應(yīng)用程序可使用不同的JVM版本。出于安全考慮,不建議在同一個(gè)系統(tǒng)中
安裝不同的JDK或JRE版本;通常最好只安裝系統(tǒng)支持的最新版本。
1.4.2JIT編譯器
雖然沒有規(guī)定,但所有流行的JVM實(shí)現(xiàn)都并非只有簡單的解釋器:除解釋器外,它們還自帶了
復(fù)雜的JIT編譯器。
啟動Java應(yīng)用程序時(shí),將首先啟動并初始化JVM。JVM啟動并初始化后,它將立即開始解釋并
運(yùn)行Java字節(jié)碼。在合適的情況下,解釋器將對程序的某些部分進(jìn)行編譯,再將原生可執(zhí)行
代碼加載到內(nèi)存中,并開始執(zhí)行這些代碼而不是經(jīng)過解釋后的Java字節(jié)碼。這樣生成的代碼
的執(zhí)行速度通常要快得多。
對代碼進(jìn)行編譯還是解釋取決于很多因素。對于經(jīng)常被調(diào)用的例程,JIT編譯器很可能對其進(jìn)
行編譯以生成原生代碼。
JIT方法的優(yōu)點(diǎn)在于,分發(fā)的文件可以是跨平臺的,且用戶無需等待整個(gè)應(yīng)用程序編譯
完畢。JVM初始化后,應(yīng)用程序?qū)⒘⒓撮_始執(zhí)行,而優(yōu)化是在幕后完成的。
1.4.3基本數(shù)據(jù)類型
JVV提供了幾個(gè)內(nèi)置的基本數(shù)據(jù)類型,這是Java未被視為純粹的OOP語言的主要原因。這些
類型的變量不是對象,且始終都包含值。
Java名稱描述和長度取值范圍(含)
byte有符號字節(jié)(ft位)-12R'127
short有符號短整型(16位)-32768"32767
int有符號整型(32位)-2「2"T
long有符號長整型(64位)-2“~2"T
float單精度浮點(diǎn)數(shù)(32位)不精確的浮點(diǎn)值
double雙精度浮點(diǎn)數(shù)(64位)不精確的浮點(diǎn)值
char單個(gè)UnicodeUTFT6字符(16位)Unicode字符0飛55535
boolean布爾值True/False
請注意,并非所有JVY語言都支持創(chuàng)建基本類型變量,并將其他一切都視為對象。你將看到,
這通常不是問題,因?yàn)镴ava類庫包含包裝基本類型的包裝對象,而包含Java在內(nèi)的大多數(shù)語
言都會在必要時(shí)自動使用這些包裝對象。這個(gè)過程被稱為自動裝箱(auto-boxing)。
1.4.4類
函數(shù)和變量都是在類中聲明的。即使是應(yīng)用程序的入口函數(shù)(在程序后動時(shí)例用的函數(shù)main。)
也是在類中聲明的。
JV"只支持單繼承模型,即類最多繼承一個(gè)類。這影響不大,因?yàn)槭褂昧嗣麨椤敖涌凇钡慕Y(jié)構(gòu)
來緩解這種影響,你將在下一章看到。接口基本上是一個(gè)函數(shù)原型(只有函數(shù)的定義,而沒有
代碼)和常量列表,編譯器要求實(shí)現(xiàn)了接口的類必須提供這些函數(shù)的實(shí)現(xiàn)。類可實(shí)現(xiàn)任意數(shù)量
的接口,但必須提供這些接口定義的每個(gè)方法的實(shí)現(xiàn)。
本書介紹的有些語言對開發(fā)人員隱藏了上述事實(shí)。例如,不同于Java,有些語言允許
在類聲明外面定義函數(shù)和變量,甚至允許可執(zhí)行代碼位于函數(shù)定義外面。還有些語言支持繼承
多個(gè)類。在內(nèi)部,這些語言巧妙地規(guī)避了JVM的限制和設(shè)計(jì)決策。
JVV類通常以包的方式進(jìn)行分組。在下一章,你將看到類是如何組織的。
1.4.5引用類型
與大多數(shù)現(xiàn)代編程語言一樣,JVM不直接操作指向?qū)ο蟮膬?nèi)存指針,而使用引用類型。引用變
量要么指向特定的類實(shí)例,要么什么都不指向。
如果一個(gè)引用變量指向特定的對象,就可使用它來調(diào)用該對象的方法或訪問其公有屬性。
如梟一個(gè)引用變量沒指向任何東西,就被稱為空引用(nullreference)。使用空引用來調(diào)用
方法或訪問屬性時(shí),將在運(yùn)行階段引發(fā)錯(cuò)誤。對于這個(gè)常見的問題,本書介紹的有些語言提供
了解決方案。
引用和空引用
請看下面的代碼:
Prodtctp=nowProduct。;
p.selName("Boxofbiscuits*):
假設(shè)這里的Product是當(dāng)前程序可使用的一個(gè)類。我們創(chuàng)建一個(gè)Product實(shí)例,并讓變量)
指向它。接下來,我們對這個(gè)對象實(shí)例調(diào)用方法setName。
NV沒有提供直接訪問這個(gè)Product對象所在內(nèi)存單元的途徑,而只提供了指向該對象的引用。
當(dāng)你使用變量P時(shí).,JVM將確定為訪問這個(gè)變量指向的對象,需要訪問哪個(gè)內(nèi)存單元。
我們在前述代碼片段中添加如下代碼行:
p=null;
p.setName("Thislinewillproduceanerroratrun-time");
可顯式地將引用設(shè)置為null。請注意,對于在方法內(nèi)聲明的變量,并非必須這樣做,因?yàn)榉?/p>
法結(jié)束時(shí),將自動清理這些變量,但這樣做也是完全合法的?,F(xiàn)在變量p是一個(gè)空引用。下一
段將介紹對象實(shí)例不再被任何引用變量指向后將發(fā)生的事情。
上述代碼能夠通過編譯,但程序運(yùn)行時(shí),最后一行將引發(fā)NullPointerException異常。女「果
沒有提供錯(cuò)誤處理功能,應(yīng)用程序?qū)⒈罎?。很多現(xiàn)代IDE都力圖發(fā)現(xiàn)這種情形,并向開發(fā)人員
發(fā)出警告。
1.4.6垃圾收集器
JVM小要求程序員在創(chuàng)建和銷毀對象時(shí)手工分配和樣放內(nèi)存塊。通常,程序員只需在需要時(shí)創(chuàng)
建龍象即可。
有一個(gè)名為GC的進(jìn)程,它每隔一段時(shí)間讓應(yīng)用程序停止執(zhí)行,并在內(nèi)存中掃描不再在作用域
內(nèi)的對象(不能被任何對象訪問的對象),再將這些對象從內(nèi)存中刪除,并收回釋放的內(nèi)存空
間。
以前,這個(gè)進(jìn)程會導(dǎo)致嚴(yán)重的性能問題,但它使用的算法已得到極大的改進(jìn)。另外,根據(jù)應(yīng)用
程序的需求,系統(tǒng)管理員可配置GC的眾多參數(shù),以更好地控制它。
開發(fā)人員應(yīng)始終牢記GC算法。如果你不斷地創(chuàng)建大量的對象,并確保它們位于作用域內(nèi)(即
讓所有這些對象都是可訪問的,如將它們存儲在應(yīng)用程序可訪問的列表中),那么遲早會導(dǎo)致
內(nèi)存耗盡,進(jìn)而引發(fā)錯(cuò)誤。
示例
假設(shè)你為一個(gè)在線商店開發(fā)了一個(gè)電子商務(wù)應(yīng)用程序,同時(shí)假設(shè)每位已登錄的用戶都有一個(gè)
ShoppingBasket實(shí)例,其中存儲了該用戶已加入到購物車中的商品。
現(xiàn)在假設(shè)今天有一位已登錄的用戶,他打算購買一塊香皂和一盒餅干。對于這位用戶,應(yīng)用程
序?qū)?chuàng)建兩個(gè)Product實(shí)例(每件商品一個(gè)),并將它們添加到ShoppingBasket的products
列表中,如下圖所示。
結(jié)賬前,這位用戶發(fā)現(xiàn)Amazon也有這樣的餅干,但價(jià)格低得多,因此決定將其從購物車中刪
除。從技術(shù)上說,應(yīng)用程序?qū)膒roducts列表中刪除相應(yīng)的Product實(shí)例。但這樣做后,表
示Chocolatecookies的Product實(shí)例就成了孤兒對象。鑒于沒有任何引用指向它,應(yīng)用程序
再也無法訪問它,如下圖所示。
過段時(shí)間后,JVM的GC啟動,它發(fā)現(xiàn)應(yīng)用程序無法訪問表示Chocolatecookies的Product
對象,因此決定將其刪除,從而釋放它占用的內(nèi)存,如下圖所示。
為避免GC將對象刪除,有多種技巧。其中一個(gè)著名的技巧是,在應(yīng)用程序需要使用大量類似
的充象時(shí),將這些對象放在一個(gè)對象池(對象列表)中。在應(yīng)用程序需要對象時(shí),只需從池中
取回一個(gè),并根據(jù)需要修改它。使用完畢并不再需要該對象時(shí),將其放回到對象池中。由于這
些充象始終在作用域內(nèi)(未用時(shí).,這些對象位于應(yīng)用程序能夠訪問的對象池中),GC不會銷
毀它們。
1.4.7向后兼容
負(fù)責(zé)維護(hù)JVM和Java類庫的人深知企業(yè)開發(fā)人員的需求:現(xiàn)在編寫的代碼最好以后也能運(yùn)行。
在向后兼容方面,JVM做得很不錯(cuò);如果你熟悉Python2和Python3,就知道情況并非總是
如此。
較新的JVM版本能夠運(yùn)行針對較舊的JVM版本編譯的應(yīng)用程序,條件是應(yīng)用程序沒有使用在較
新的JVM版本中已刪除的API或技術(shù)。例如,在Java8JVM實(shí)例上運(yùn)行的項(xiàng)目可加載并使用
針店Java6編譯的庫,但反過來行不通,即在Java6JVM實(shí)例上運(yùn)行的應(yīng)用程序不能加載針
對更高版本編譯的類。
當(dāng)然,與其他平臺和語言一樣,負(fù)責(zé)維護(hù)JDK和Java類庫的人必須時(shí)小時(shí)地?fù){棄一些類和技
術(shù)。在向后兼容性方面,JVM雖然存在問題,但總體而言比眾多其他的平臺和語言要好得多。
另外,通常僅當(dāng)有合適的替代品后,才會將API刪除。
1.4.8構(gòu)建工具
在項(xiàng)目比較簡單的年代,為自動化編譯和打包過程,使用的是簡單的批文件或操作系統(tǒng)Shell
腳本文件。隨著項(xiàng)目越來越復(fù)雜,定義這樣的腳本越來越難。另外,對于不同的操作系統(tǒng),必
須編寫完全不同的腳本。
不久后,第一套專用的Java構(gòu)建工具應(yīng)運(yùn)而生。它們使用的是XML構(gòu)建文件,讓你能夠編寫
跨平臺的腳本。最初,必須編寫冗長而繁瑣的腳本;但后來,這些工具采用了約定優(yōu)先于配置
的范式。遵循這些工具指定的約定時(shí),需要編寫的代碼少得多;但如果你面對的不是默認(rèn)情形,
可能需要花很大的精力來讓工具按你希望的做。為自動化構(gòu)建過程,較新的工具放棄了XM)
文件,轉(zhuǎn)而提供了腳本語言。
在這些工具中,很多都提供了如下功能。
?內(nèi)置的依賴管理器:能夠從著名的網(wǎng)絡(luò)倉庫下載附加庫。
?自動運(yùn)行單元測試,并在測試失敗時(shí)停止打包。
JDK本身沒有提供構(gòu)建工具,但幾乎每個(gè)項(xiàng)目都至少使用了下面一個(gè)開源的構(gòu)建自動化匚具。
?ApacheAnt(沒有內(nèi)置的依賴管理器,使用的是基于XML的構(gòu)建腳本)。
?ApacheMaven(通過使用XML文件引入了約定優(yōu)先于配置的原則,并使用插件)。
?Gradle(構(gòu)建腳本是使用Groovy或Kotlin編寫的)。
只要使用的是流行的IDE,JVM程序員就無需過多地考慮構(gòu)建自動化工具,因?yàn)樗蠭DE都能
夠生成構(gòu)建腳本。如果要獲得更大的控制權(quán),可手工編寫腳本,并讓IDE根據(jù)你編寫的腳本來
編譯、測試和運(yùn)行項(xiàng)目。
1.5Java版本
Java有多個(gè)不同的版本,其中每個(gè)版本都針對不同的用例。多年來,有些版本的名稱發(fā)生了
翻天覆地的變化,當(dāng)前版本的名稱如下:
?Java標(biāo)準(zhǔn)版(JavaSE)
?Java企業(yè)版(JavaEE)
?Java微型版(JavaME)
1.5.1JavaSE
這是最重要的版本,大家說到Java時(shí),通常指的是就是這個(gè)版本。本書只考慮JavaSE平臺。
這個(gè)版本用于臺式機(jī)利服務(wù)器。另外,你將看到,還有一個(gè)嵌入式版本,用于Raspberry"
的Linux發(fā)行版就自帶了這種嵌入版本。JavaSE自帶了完整的Java類庫,還包含經(jīng)典的Swing
GUI工具包,而大多數(shù)版本還包含較新的JavaFXGUI工具包。
注意:較新的JavaSEEmbedded更新刪除了JavaFX工具包。在RaspberryPi上安裝
這個(gè)更新后,JavaFX組件將消失。Oracle以開源的方式提供了用于RaspberryPi的JavaFX,
讓高階用戶能夠下載并編譯它。
JavaSE主要用于創(chuàng)建獨(dú)立的控制臺應(yīng)用程序、桌面GUI應(yīng)用程序和無界面(headless)應(yīng)用
程序,還可用于創(chuàng)建外部庫。
1.5.2JavaEE
JavaEE建立在JavaSE的基礎(chǔ)之上,因此要求安裝JavaSE。它添加了類型眾多的API。Java
EE應(yīng)用程序通常運(yùn)行在JVM應(yīng)用程序服務(wù)器上。本書不會深入介紹JavaEE,但時(shí)不時(shí)會提及
它,因?yàn)樗荍ava平臺的重要補(bǔ)充,對企業(yè)開發(fā)人員來說尤其如此。
Oracle網(wǎng)站沒有提供獨(dú)立的JavaEE版本,你必須下載與所需JavaEE平臺版本兼容的應(yīng)用
程序服務(wù)器。有些IDE也自帶了JavaEE應(yīng)用程序服務(wù)器,這將在下一章討論。
JavaEE標(biāo)準(zhǔn)只描述了必須提供的APT,而沒有指定實(shí)現(xiàn)方式。具體如何實(shí)現(xiàn)符合標(biāo)準(zhǔn)的API,
由與JavaEE兼容的應(yīng)用程序服務(wù)器決定。
示例:兩款應(yīng)用程序服務(wù)器實(shí)現(xiàn)的Java持久化API
JavaEE描述了Java持久化API(JavaPersistenceAPT,JPA)<,這是一個(gè)對象關(guān)系映射器
(objectrelationmapper,ORM)API,位于Java對象和關(guān)系型數(shù)據(jù)庫(通常是SQL數(shù)據(jù)庫,
如Oracle、OracleMySQL、PostgreSQL等)之間;使用它只需編寫幾行代碼,就可將JVM對
象的內(nèi)容寫入數(shù)據(jù)庫,反之(從數(shù)據(jù)庫讀取數(shù)據(jù)并將其加入對象中)亦然。
Oracle提供的JavaEE參考實(shí)現(xiàn)是一個(gè)開源的應(yīng)用程序服務(wù)器,名為GlassFish。GlassFish
包含開源項(xiàng)目EclipseLink,該項(xiàng)目實(shí)現(xiàn)了JPA標(biāo)準(zhǔn)。RedHat出品的WildFly也是一款開源
的JavaEE應(yīng)用程序服務(wù)器,其中包含RedHat自己開發(fā)的ORM開源項(xiàng)目Hibernate,這個(gè)項(xiàng)
目也實(shí)現(xiàn)了JPA標(biāo)準(zhǔn),但更流行。
如果只使用JPA標(biāo)準(zhǔn)規(guī)定的功能,則使用哪種實(shí)現(xiàn)無關(guān)緊要,但要使用其他功能,選擇使用哪
種實(shí)現(xiàn)就很重要。
如果你不喜歡某個(gè)應(yīng)用程序服務(wù)器廠商的設(shè)計(jì)決策,通??赊D(zhuǎn)而使用其他實(shí)現(xiàn)。對于
選擇空間,JVM開發(fā)人員非常在乎!
1.5.3JavaME
在iOS和Android面世前,JavaME是重要的功能手機(jī)和智能手機(jī)游戲和應(yīng)用程序開發(fā)平臺。
iOS和Android都不支持JavaME應(yīng)用程序,因此它現(xiàn)在已不再是主角。
JavaME包含Java類庫的一部分,同時(shí)提供了其他一些與移動設(shè)備交互的API。JavaME獲得
了重生,它現(xiàn)在名為JavaMEEmbedded,可用于商業(yè)IoT設(shè)備。
1.6其他JVM語言
為推廣Java語言和平臺,Sun很早就公布了JVM規(guī)范。這個(gè)文檔旨在供那些要自己動手編寫
JVV實(shí)現(xiàn)的開發(fā)人員參考,這些JVY實(shí)現(xiàn)可能是為那些沒有官方JVM實(shí)現(xiàn)的平臺編寫的。這個(gè)
文檔描述了JVM可執(zhí)行的低級命令、必須提供的數(shù)據(jù)結(jié)構(gòu)、內(nèi)存訪問規(guī)則、Java字節(jié)碼文件
格式.class等。
這個(gè)規(guī)范的發(fā)布讓其他語言的設(shè)計(jì)者能夠嘗試Java字節(jié)碼,因此不久后其他語言也能夠編譯
成這種格式。這雖然不是Java設(shè)計(jì)者的初衷,但Sun(和后來的Oracle)樂見其成。它便是
如此地樂見其成,以至于僅僅為方便JVM支持動態(tài)語言而添加了新功能。
本芋將介紹與其他JV.M語言相關(guān)的如下主題。
?為何要放棄Java轉(zhuǎn)而使用其他語言進(jìn)行JVM開發(fā)?
?在同一個(gè)項(xiàng)目中使用多種語言的可能性以及這樣做可能帶來的問題。
?使用不同于主項(xiàng)目使用的語言編寫單元測試。
1.6.1為何選擇其他語言
考慮到Java語言最初就是為在JVM上運(yùn)行而設(shè)計(jì)的,怎么會有人選擇使用其他語言來進(jìn)行JVM
開發(fā)呢?
開發(fā)人員這樣做的原因有多個(gè):
是——種非常繁瑣的語言:
?J并a非va所有人都喜歡靜:態(tài)建嘉言,且靜態(tài)語言并非在任何情況下都是最佳選擇;
?Java類庫缺少一些經(jīng)常需要用到的類。
?Java是一種非常繁瑣的語言
Java以繁瑣著稱。經(jīng)過多年的修訂后,Java已不再那么繁瑣,但使用很多其他的語言時(shí),完
成同樣的任務(wù)所需的代碼更少。
我們來看一個(gè)簡單的示例。
在Java中,標(biāo)準(zhǔn)的可修改對象通常類似于下面這樣:
classPerson{
privateStringname:
publicPerson(Stringname){
this,name=name;
}
publicStringgctNamcO\
returnname;
}
publicvoidsetName(Stringname){
this,name=name;
}
}
而使用Kotlin時(shí),只需下面一行代碼就能實(shí)現(xiàn)同樣的功能(以及其他功能):
dataclassPerson(valname:String)
這可不是開玩笑。編譯這行代碼時(shí),Kotlin將自動實(shí)現(xiàn)Java示例中定義的方法;實(shí)際上,它
還會添加其他較為常用的方法。第4章將討論這些額外的方法。
雖然使用其他語言可極大地提高效率,但Java也沒有看起來那么糟糕。所有現(xiàn)代IDE
編程工具都能自動生成Java樣板代碼,如前述示例中的樣板代碼。為此,你只需按下一個(gè)簡
單的組合鍵即可。
?Java并非對所有的人或在任何情況下都是理想選擇
雖然Java8新增了一些重要的函數(shù)式編程功能,但從本質(zhì)上說,它依然是一種靜態(tài)的命令式
語言。并非所有的開發(fā)人員都喜歡這種編程風(fēng)格。如果必須使用靜態(tài)語言來編寫代碼,Python
或Ruby程序員可能會哭暈在廁所。有鑒于此,有些團(tuán)隊(duì)放棄Java轉(zhuǎn)而選擇使用其他語言來進(jìn)
行JVM開發(fā)。
另外,對于有些問題,使用動態(tài)編程語言解決起來要優(yōu)雅得多;同時(shí)對于必須執(zhí)行復(fù)雜并發(fā)操
作的項(xiàng)目來說,函數(shù)式編程風(fēng)格通常更合適。最后,對于有些哭和框架,通過某些語言來使用
讓人感覺更為自然。
?Java類庫缺失的類
Java類庫是一個(gè)龐大的庫,但它畢竟是20多年前推出的,因此在有些情況下缺少必要的類。
在大多數(shù)情況下,功能缺失的問題可通過添加JVV生態(tài)系統(tǒng)中免費(fèi)的開源插件庫來解決,但如
果選擇使用內(nèi)置了這些功能的語言,不僅更方便,還可節(jié)省時(shí)間。
例如,對于極其常用的JSON標(biāo)準(zhǔn),JavaSE8的Java類庫就沒有提供原生支持。流行的插件
庫Jackson和GoogleGS0N提供了JS0N支持;另外,較新的JavaEE平臺版本也提供了支持
JSON的APE本書介紹的一些語言提供了原生的JSON支持。
另一個(gè)問題是,要使用Java類庫中的一-些常用類,必須編寫大量的樣板代碼。對于Java類庫
中的眾多常用類,諸如Groovy等語言都提供了包裝器,讓這些API使用起來輕松得多。
1.6.2在同一個(gè)項(xiàng)目中使用多種JVM語言
很多語言都能夠與Java互操作,因此也能夠與其他JVM語言互操作。這是通過盡可能為數(shù)據(jù)
結(jié)構(gòu)使用標(biāo)準(zhǔn)Java類庫并像Java那樣編譯方法來實(shí)現(xiàn)的。
在Java項(xiàng)目中,經(jīng)常使用其他語言來編寫某些類,但這樣做可能帶來一些問題:
?構(gòu)建過程將復(fù)雜得多;
?很多語言要求使用自己的運(yùn)行時(shí)類,這可能帶來問題。
?構(gòu)建過程更復(fù)雜
使用多種語言時(shí),必須調(diào)整構(gòu)建腳本,這可能導(dǎo)致情況非常復(fù)雜。例如,如果Java項(xiàng)目使用
了用Groovy編譯的類,編譯順序?qū)⒎浅V匾?,即必須先編譯Groovy類,再編譯Java代四。
如果Groovy代碼使用了Java項(xiàng)目中的自定義類,情況將更加復(fù)雜。
你將在第11章看到,Groovy比較特殊。Groovy編譯器能夠編譯大部分Java代碼,因
為從很大程度上說,Groovy語言與Java語言兼容。在沒法這樣做或這樣做不可取時(shí),有一個(gè)
用于構(gòu)建工具ApacheYaven的編譯器插件,使用它可解決構(gòu)建過程中面臨的問題。
一種解決之道是將代碼分成多個(gè)子項(xiàng)目,并在構(gòu)建工具中將生成的庫作為主項(xiàng)目的需求列出。
有些語言提供了另一種解決方案:它們提供了自定義類,讓你能夠在Java(或其他JVM語言)
中調(diào)用這些語言的源代碼。被這些類加載時(shí),源代碼將動態(tài)地編譯為Java字節(jié)碼。其他語言
實(shí)現(xiàn)了在Java代碼中嵌入腳本語言的官方標(biāo)準(zhǔn);附錄A討論Oracle的JavaScript解釋器
Nashorn時(shí),將簡要地討論這一點(diǎn)。
?語言運(yùn)行時(shí)庫
從某種程度上說,這與構(gòu)建并發(fā)癥相關(guān)。很多JVM語言都要求在編譯后的程序中包含支持率,
這些庫通常定義了語言特有的數(shù)據(jù)結(jié)構(gòu)以及編譯得到的Java字節(jié)碼調(diào)用的內(nèi)部支持方法。
這通常不是問題,但如果項(xiàng)目的依賴項(xiàng)(或依賴項(xiàng)的依賴項(xiàng))是使用不同的語言版本編寫的,
就可能出現(xiàn)問題。如果同一個(gè)項(xiàng)目的多個(gè)庫要求使用同一個(gè)運(yùn)行時(shí)庫的不同版本,情況將更為
復(fù)雜:編譯或運(yùn)行項(xiàng)目時(shí),可能出現(xiàn)令人費(fèi)解的錯(cuò)誤消息、。
這被稱為依賴惡夢(dependencyhell),但這并非是在同一個(gè)項(xiàng)Fl中使用多種語言特有的現(xiàn)
象,而是每個(gè)開發(fā)人員都應(yīng)知道的現(xiàn)象。打算在同一個(gè)項(xiàng)目中變用多種語言的開發(fā)人員還必須
明白,語言運(yùn)行時(shí)庫可能導(dǎo)致最終程序的規(guī)模急劇增大:有叱運(yùn)行時(shí)庫還包含其依賴項(xiàng).這將
增大出現(xiàn)依賴惡夢的風(fēng)險(xiǎn)。通常,語言的文檔或官網(wǎng)都詳細(xì)說明了其依賴項(xiàng)。
與很多框架設(shè)計(jì)者一樣,很多語言設(shè)計(jì)者都對這些問題心中有數(shù),并采取了措施降低
這些問題出現(xiàn)的風(fēng)險(xiǎn)。例如,對于自己使用的較流行的依賴項(xiàng),他們進(jìn)行了重命名,以防發(fā)生
類名沖突。
1.6.3使用另一種語言編寫單元測試
使用其他語言編寫的單元測試來對Java代碼進(jìn)行測試很常見c正如你在本章前面看到的,相
比于Java,使用其他語言編寫的代碼可能緊湊得多,這些語言非常適合用來編寫小型、具體
而易于理解的單元測試。
鑒于僅在運(yùn)行單元測試時(shí)才會用到這些語言的運(yùn)行時(shí)庫,因此無需在編譯得到的主項(xiàng)目中包含
它們。
你將在第11章看到,在這樣的情形下,非常適合使用Groovy。Groovy提供了一些便
利的單元測試編寫功能,其中包括內(nèi)置的assert語句,這種語句在傳入的值與期望值不同時(shí)
將打印非常詳盡而易于理解的輸出。。
1.7小結(jié)
本章非常簡略地描述了JVMo首先介紹了JVV向開發(fā)人員提供的功能、JVM的常見用途以及最
重要的JVM概念;接下來探索了Java版本;最后介紹了其他JVM語言,以及開發(fā)人員放棄Java
轉(zhuǎn)而使用其他語言進(jìn)行JVM開發(fā)的原因。
在下一章,我們將安裝并詳細(xì)介紹JDK,還將詳細(xì)介紹Java類庫并安裝其他開發(fā)工具,為動
手開發(fā)做好準(zhǔn)備。
第2章Java虛擬機(jī)開發(fā)
本章深入介紹Java虛擬機(jī)(JVM),重點(diǎn)是每個(gè)JVM開發(fā)人員都必須知道的概念,而不管他選
擇使用的是哪種編程語言。本章涵蓋如下主題:
?Java開發(fā)包(JDK);
?使用包來組織類;
?Java類庫;
?從命令行運(yùn)行JVM應(yīng)用程序;
?安裝Eclipse集成開發(fā)環(huán)境(EclipseIDE)。
本書涵蓋Windows、macOS和Linux(Ubuntu)操作系統(tǒng),但展示路徑時(shí)通常使用Windows風(fēng)
格。如果你使用的是macOS或Linux,務(wù)必按相應(yīng)操作系統(tǒng)的規(guī)則修改路徑。
2.1JDK
要進(jìn)行JVM開發(fā),必須安裝JDKJDK包含Java運(yùn)行時(shí)環(huán)境(JavaRuntimeEnvironment,JRE)^
Java編譯器以及各種開發(fā)工具(本章將介紹其中的一些)。艮J便你的大部分開發(fā)工作都將使
用其他語言而不是Java來完成,也強(qiáng)烈建議你安裝完整的JDK,因?yàn)楹芏嘀匾拈_發(fā)工具都
必須安裝完整的JDK才能運(yùn)行。另外,你遲早都將用到一些只有JDK才有的工具。
安裝較新的用于RaspberryPi的Linux發(fā)行版時(shí),如果使用默認(rèn)的Raspian安裝選項(xiàng),將自
動安裝JavaSEEmbedded8JDK,但提供的版本通常不是最新的。其他主要的操作系統(tǒng)默認(rèn)
安裝的JDK如何不得而知。木節(jié)介紹如下與JDK相關(guān)的主題:
?安裝JDK(WindowsniacOS和Linux);
?探索JDK;
?JREo
2.1.1安裝JDK
這里只介紹如何安裝Oracle的JDK8實(shí)現(xiàn)。如果你已安裝與JavaSE8平臺完全兼容的J3K
實(shí)現(xiàn),包括開源的OpenJDK8或IBM的J9JDK8,通常也完全可行,因此你可以跳過本節(jié)。
非Oracle的JDK實(shí)現(xiàn)并不一定包含本書討論的所有功能,必要時(shí)我們將指出例外情況。
無論你使用的是哪種操作系統(tǒng),都必須創(chuàng)建一個(gè)名為JAVAJIOME的環(huán)境變量,并讓它指向」DK
安裝目錄(在非開發(fā)計(jì)算機(jī)中為JRE所在的目錄)。對于本鬲涵蓋的操作系統(tǒng)(Windows.macOS
和Linux),我們將說明如何創(chuàng)建這樣的環(huán)境變量。很多重要的JVM工具都要用到這個(gè)變量,
包括構(gòu)建工具和應(yīng)用程序服務(wù)器。本節(jié)將介紹如何完成如下工作:
?下載JDK;
?在Windows系統(tǒng)中安裝JDK;
?在macOS系統(tǒng)中安裝JDK;
?在Linux系統(tǒng)中安裝JDK;
?下載JavadocAPI文檔。
?下載JDK
Oracle提供的用于Windows、macOS和Linux的JDK實(shí)現(xiàn)可從Oracle網(wǎng)站下載。對于有些平
臺,只有64位的JDK,而對于其他平臺,有32位和64位的。
使用你喜歡的瀏覽器訪問Oracle的Java主頁(http:〃www.oracle,com/java),如下圖所示。
?卜④廣“MV.-htm'
:*Rnr?l>n>-liwrrcSewch
ProductsSoMticnsStoreSupperTrainingPartre-iAt>2<rtQIN
JavaSonware
JavaYourNext(Cloud)
Javzi?th*eofkfsfxojr<t-nming
JBftr.」蒲同forCcroirrer?
OverviewRa”Techncioglei
要下載JDK,需執(zhí)行如下步驟。
(1)本書編寫期間,該網(wǎng)頁包含一個(gè)JavaforDevelopers,單擊該按鈕將進(jìn)入Software
Downloads部分。
(2)在列表中找到并單擊JavaSE(包含JavaFX)。如果它旁邊有鏈接EarlyAccess,請注
意不要單擊該鏈接。
(3)進(jìn)入JavaSEDownloads頁面。單擊JDKF方的Download按鈕。
(4)根據(jù)你使用的操作系統(tǒng)平臺和體系結(jié)構(gòu),找到并單由相應(yīng)的版本。
(5)如果你同意了許可條款,將下載相應(yīng)版本的JDK。
?在Windows系統(tǒng)中安裝JDK
對于Windows操作系統(tǒng),JDK有32位和64位的版本。你只需總行下載的可執(zhí)行文件并按說明
做即可。請將JDK安裝路徑記錄下來,因?yàn)楹竺嬉玫健?/p>
請使用默認(rèn)設(shè)置,這將隨JDK安裝JRE。強(qiáng)烈建議確保JRE和JDK的版本同步,因此使用JDK
安裝程序安裝JRE是最佳選擇。Oracle指出JDK始終是在系統(tǒng)級安裝的,因此其他所有用戶
都可使用它。
安裝完畢后,需要添加或修改一些環(huán)境變量。這里介紹如何在Windows10中這樣做,如果你
使用的是其他較新的Windows版本,做法應(yīng)與之類似。
(1)右擊Windows“開始”按鈕并選擇“系統(tǒng)”,在出現(xiàn)的窗口中,單擊左邊的“高級系統(tǒng)設(shè)
置”。
(2)這將打開“系統(tǒng)屬性”對話框。單擊“環(huán)境變量”按鈕,這將打開如下圖所示的“環(huán)境變
量”對話框:
EnvironmentVariablesX
>crvariablesforVincent
VariableValje
DOCKER.TOOLBOX.INSTAL..C:\PfOgFilesyDockei"oolbox
PATHC:\Progr2mFil?\Mcrcurial^zXUsrrs^Vinccnt'iAppDataVLocarKatomV.
TEMP%USERPFOFILE%\AppData'?Locar\Tenp
TMP%LlSERFFOFILE%\AppDd^Locar\Tenip
MF-A.E(fiJDelete
Systemvarable:
VsnabeValueA
|JAVA_HOMFC:\lava\JDIGidk.1息0.112R
NUMBER.OF.PROCESSORS8
OSWindowsNT
PathC:\Java'JDK\jdkJ,3.0J⑵二八Pythcn27\C:\Dev\GNU$malltak\:..
PATHEXT(0M;,R;.SAT;.CM6VBS;V3EJS;JSe.V$F;M5H;JVISC
PROCESSCR_ARCHTECTUREAMD&4
PROCESSORIDENTiFERIntelaramtfv6Medel5CSteooina3Genuinelntd
N3“?Ecfit...Ddete
OK|Cantel
(3)在這個(gè)對話框底部的“系統(tǒng)變量”部分查找變量JAVA_H0;IE。如果沒有找到,就單擊按鈕
“新建”,否則對既有的JAVAJ40ME進(jìn)行編輯。
(4)將變量名設(shè)置為JAVAJOME,并將值設(shè)置為JDK安裝目錄的完整路徑,再單擊“確定”按
鈕關(guān)閉打開的對話框。
(5)找到既有的變量Path,并在其中添加JDK安裝目錄下的子目錄bin的完整路徑;別忘了
用字符;將不同的目錄分隔。
為驗(yàn)證安裝,可執(zhí)行如下步驟。
(1)打開一個(gè)命令提示符窗口(為此,可單擊“開始”按鈕,輸入emd并按回車鍵)。
(2)輸入javac-version并按回車鍵。
你將看到一個(gè)版本號,它與下載的JDK版本相同。如果不是這樣,請核實(shí)你是否正確地修改了
環(huán)境變量,并確保你新打開了一個(gè)命令提示符窗口,而不是使用以前打開的命令提示符窗口。
?在
溫馨提示
- 1. 本站所有資源如無特殊說明,都需要本地電腦安裝OFFICE2007和PDF閱讀器。圖紙軟件為CAD,CAXA,PROE,UG,SolidWorks等.壓縮文件請下載最新的WinRAR軟件解壓。
- 2. 本站的文檔不包含任何第三方提供的附件圖紙等,如果需要附件,請聯(lián)系上傳者。文件的所有權(quán)益歸上傳用戶所有。
- 3. 本站RAR壓縮包中若帶圖紙,網(wǎng)頁內(nèi)容里面會有圖紙預(yù)覽,若沒有圖紙預(yù)覽就沒有圖紙。
- 4. 未經(jīng)權(quán)益所有人同意不得將文件中的內(nèi)容挪作商業(yè)或盈利用途。
- 5. 人人文庫網(wǎng)僅提供信息存儲空間,僅對用戶上傳內(nèi)容的表現(xiàn)方式做保護(hù)處理,對用戶上傳分享的文檔內(nèi)容本身不做任何修改或編輯,并不能對任何下載內(nèi)容負(fù)責(zé)。
- 6. 下載文件中如有侵權(quán)或不適當(dāng)內(nèi)容,請與我們聯(lián)系,我們立即糾正。
- 7. 本站不保證下載資源的準(zhǔn)確性、安全性和完整性, 同時(shí)也不承擔(dān)用戶因使用這些下載資源對自己和他人造成任何形式的傷害或損失。
最新文檔
- 2025飲料分銷代理合同
- 2025銷售勞動合同模板
- 2025公司服裝供貨合同
- 2025維修合同 設(shè)備維修合同
- 2025辦公室租賃合同附加協(xié)議
- 瓷磚銷售類勞動合同協(xié)議
- 班干部任職合同協(xié)議
- 病人護(hù)理中介合同協(xié)議
- 電力作業(yè)人員合同協(xié)議
- 皮卡配件供貨合同協(xié)議
- 非洲自然災(zāi)害
- 2023詩詞大會知識競賽200題題庫(含答案)
- TL226 大眾試驗(yàn)測試標(biāo)準(zhǔn)
- 2023借款協(xié)議書Word模板
- 生產(chǎn)設(shè)備拆除工程施工方案
- (完整版)年產(chǎn)30萬噸合成氨合成工段工藝設(shè)計(jì)畢業(yè)論文
- 無障礙公共設(shè)施建設(shè)的問題及其對策研究
- 臨床醫(yī)學(xué)(???畢業(yè)綜合考復(fù)習(xí)題
- 石家莊市存量房買賣合同
- 思想道德與法治2023版教學(xué)設(shè)計(jì)第六章 學(xué)習(xí)法治思想 提升法治素養(yǎng)
- 自來水廠調(diào)試方案
評論
0/150
提交評論