1. 程式人生 > 其它 >編譯型程式語言與解釋型程式語言的區別

編譯型程式語言與解釋型程式語言的區別

我們先看編譯型,其實它和組合語言是一樣的:也是有一個負責翻譯的程式來對我們的原始碼進行轉換,生成相對應的可執行程式碼。這個過程說得專業一點,就稱為編譯(Compile),而負責編譯的程式自然就稱為編譯器(Compiler)。如果我們寫的程式程式碼都包含在一個原始檔中,那麼通常編譯之後就會直接生成一個可執行檔案,我們就可以直接運行了。但對於一個比較複雜的專案,為了方便管理,我們通常把程式碼分散在各個原始檔中,作為不同的模組來組織。這時編譯各個檔案時就會生成目標檔案(Object file)而不是前面說的可執行檔案。一般一個原始檔的編譯都會對應一個目標檔案。這些目標檔案裡的內容基本上已經是可執行程式碼了,但由於只是整個專案的一部分,所以我們還不能直接執行。待所有的原始檔的編譯都大功告成,我們就可以最後把這些半成品的目標檔案“打包”成一個可執行檔案了,這個工作由另一個程式負責完成,由於此過程好像是把包含可執行程式碼的目標檔案連線裝配起來,所以又稱為連結(Link),而負責連結的程式就叫就叫連結程式(Linker)。連結程式除了連結目標檔案外,可能還有各種資源,像圖示檔案啊、聲音檔案啊什麼的,還要負責去除目標檔案之間的冗餘重複程式碼,等等。連結完成之後,一般就可以得到我們想要的可執行檔案了。

一個完整的編譯系統與 一個用C編寫的程式hello.c的編譯過程

現在再看看解釋型。從字面上看,“編譯”和“解釋”的確都有“翻譯”的意思,它們的區別則在於翻譯的時機安排不大一樣。打個比方:假如你打算閱讀一本外文書,而你不知道這門外語,那麼你可以找一名翻譯,給他足夠的時間讓他從頭到尾把整本書翻譯好,然後把書的母語版交給你閱讀;或者,你也立刻讓這名翻譯輔助你閱讀,讓他一句一句給你翻譯,如果你想往回看某個章節,他也得重新給你翻譯。

兩種方式,前者就相當於我們剛才所說的編譯型:一次把所有的程式碼轉換成機器語言,然後寫成可執行檔案;而後者就相當於我們要說的解釋型:在程式執行的前一刻,還只有源程式而沒有可執行程式;而程式每執行到源程式的某一條指令,則會有一個稱之為解釋程式的外殼程式將原始碼轉換成二進位制程式碼以供執行,總言之,就是不斷地解釋、執行、解釋、執行。所以,解釋型程式是離不開解釋程式的。解釋型程式中,由於程式總是以原始碼的形式出現,因此只要有相應的直譯器,移植幾乎不成問題。編譯型程式雖然原始碼也可以移植,但前提是必須針對不同的系統分別進行編譯,對於複雜的工程來說,的確是一件不小的時間消耗,況且很可能一些細節的地方還是要修改原始碼。而且,解釋型程式省卻了編譯的步驟,修改除錯也非常方便,編輯完畢之後即可立即執行,不必像編譯型程式一樣每次進行小小改動都要耐心等待漫長的 Compiling…Linking… 這樣的編譯連結過程。不過凡事有利有弊,由於解釋型程式是將編譯的過程放到執行過程中,這就決定了解釋型程式註定要比編譯型慢上一大截,像幾百倍的速度差距也是不足為奇的。

編譯型與解釋型,兩者各有利弊。前者由於程式執行速度快,同等條件下對系統要求較低,因此像開發作業系統、大型應用程式、資料庫系統等時都採用它,像 C/C++、Pascal/Object、Pascal(Delphi)、VB 等基本都可視為編譯語言,而一些網頁尾本、伺服器指令碼及輔助開發介面這樣的對速度要求不高、對不同系統平臺間的相容性有一定要求的程式則通常使用解釋性語言,如 Java、JavaScript、VBScript、Perl、Python 等等。

但既然編譯型與解釋型各有優缺點又相互對立,所以一批新興的語言都有把兩者折衷起來的趨勢。說到這裡,我們有必要說一下 Java 。

JAVA 語言是一種編譯型-解釋型語言

,同時具備編譯特性和解釋特性。其實,確切的說 Java 就是解釋型語言,其所謂的(預)編譯過程只是將 .java 檔案程式設計成平臺無關的位元組碼 .class 檔案(生成的程式碼是介於機器碼和Java原始碼之間的中介程式碼),並不是向 C 一樣編譯成可執行的機器語言。作為編譯型語言,JAVA 程式要被統一編譯成位元組碼檔案——檔案字尾是 .class 。此種檔案在 Java 中又稱為類檔案。Java 類檔案不能在計算機上直接執行,它需要被 JVM(Java 的虛擬機器平臺,可視為直譯器)翻譯成本地的機器碼後才能執行,而 Java 虛擬機器的翻譯過程則是解釋性的。Java 位元組碼檔案首先被載入到計算機記憶體中,然後讀出一條指令,翻譯一條指令,執行一條指令,該過程被稱為 Java 語言的解釋執行。而在現實中,Java 開發工具 JDK 提供了兩個很重要的命令來完成上面的編譯和解釋(翻譯)過程。兩個命令分別是 java.exe 和 javac.exe,前者載入 Java 類檔案,並逐步對位元組碼檔案進行編譯,而另一個命令則對應了 Java 語言的解釋(javac.exe)過程。在次序上,Java 語言是要先進行編譯的過程,接著解釋執行。這樣既保留了原始碼的高抽象、可移植的特點,又已經完成了對原始碼的大部分預編譯工作,所以執行起來比“純解釋型”程式要快許多。

總結

C/C++、Pascal、Go、彙編等,必須在程式執行之前將所有程式碼都翻譯成二進位制形式,也就是生成可執行檔案,使用者拿到的是最終生成的可執行檔案,看不到原始碼。

這個過程叫做編譯(Compile),這樣的程式語言叫做編譯型語言,完成編譯過程的軟體叫做編譯器(Compiler)。

而有的程式語言,如 Shell、JavaScript、Python、PHP 等,需要一邊翻譯一邊執行,不會生成任何可執行檔案,使用者必須拿到原始碼才能執行程式。程式執行後會即時翻譯,翻譯完一部分執行一部分,不用等到所有程式碼都翻譯完。

這個過程叫做解釋,這樣的程式語言叫做解釋型語言或者指令碼語言(Script),完成解釋過程的軟體叫做直譯器。

編譯型語言的優點是執行速度快、對硬體要求低、保密性好,適合開發作業系統、大型應用程式、資料庫等。

指令碼語言的優點是使用靈活、部署容易、跨平臺性好,非常適合 Web 開發以及小工具的製作。


參考: https://www.jianshu.com/p/d21010003bb7 http://c.biancheng.net/view/4136.html