.NET程式執行原理及基本概念詳解

詩意的遠方發表於2020-07-09

一、引言

我們知道在Java中有虛擬機器,程式碼執行時虛擬機器把Java語言編譯成與機器無關的位元組碼,然後再把位元組碼編譯成機器指令執行,那麼在.NET中程式是如何執行的呢?

其實執行原理是一樣的,.NET中的虛擬機器是CLR(公共語言執行時),無論是C#程式還是VB程式,首先會由CLR編譯成與平臺無關的中間語言IL,然後由公共語言執行時CLR的

即時編譯器JIT編譯成機器程式碼,再由CPU去執行它。所以說.NET程式也是需要二次編譯才能執行,其中涉及的相關術語解釋如下:

  1. IL/MSIL (Microsoft Intermediate Language) :微軟中間語言 ,IL是MSIL的縮寫,譯為中間語言,.NET程式下的所有語言都會編譯成中間語言,所以他們之間可以相互呼叫,與語言無關;
  2. CTS (Common Type System):通用的資料型別系統,比如C#呼叫VS語言程式,雖然他們各自的資料型別定義不一樣,但是最終都會轉化為通用型別,比如c#中的int,VB語言中的integer,在CLS中都會轉化為System.int32,所以這兩者之間的程式可以相互呼叫;
  3. CLS(Common Language Specification):公共語言規範;
  4. CLR (Common Language Runtime):公共語言執行時,也有的叫公共語言執行庫;
  5. JIT (Just in time):即時編譯器。

二、控制檯程式專案結構解釋

 為了更好的分析.NET程式的執行原理,首先我們在VS2019中新建一個控制檯應用程式,名稱為:MyFirstAPP,成功後,我們可以看到系統為我們建立了以下結構:

 這些檔案結構的基本含義為:

(1)Properties資料夾:(屬性資料夾)

AssemblyInfo.cs檔案:這個主要儲存程式釋出後的版權資訊,我們點選   屬性=》 程式集資訊 可以相關資訊。

 (2)引用:這是我們可以新增其他應用程式集,比如系統類庫、其他專案或者模組的類庫,Webservice服務等

 (3)Program.cs 檔案: 這個是專案自定義的程式碼類,開啟以後,我們看到如下程式碼:

 1 using System;
 2 using System.Collections.Generic;
 3 using System.Linq;
 4 using System.Text;
 5 using System.Threading.Tasks;
 6 
 7 namespace MyFirstApp
 8 {
 9     class Program
10     {
11         static void Main(string[] args)
12         {
13             Console.WriteLine("HelloWorld!");
14         }
15     }
16 }

我們大概分析一下系統預設生成的這些程式碼:

  1. using表示引用名稱空間。如果我們需要引用其他類庫的中程式碼,需要新增引用,相當於Java中的import,如果不使用using引入名稱空間,那麼我們使用類的時候,就需要通過“名稱空間.類名”方式使用;
  2. namespace表示宣告名稱空間。名稱空間是用來組織和重用知程式碼的,我們所有的類必須要歸到指定的名稱空間中。
  3. class表示宣告類。名稱空間中包括類,類是.net程式基本執行單元。
  4. static void Main(string[] args)表示宣告一個靜態方法,方法名稱為Main,args表示命令引數,這個方式不能修改,否則程式將不能啟動,因為這是整個程式的入口點。

三、.NET專案編譯

我們點選編譯,然後開啟專案資料夾,在  bin\Debug  下發現系統生成了三個檔案,這三個檔案的含義如下:

 

  1. exe檔案:編譯後生成的可執行檔案,裡面是MSIL中間語言。專案釋出或給使用者可以直接執行的程式;
  2. dll檔案:編譯後生成的動態連結庫檔案。裡面也是MSIL中間語言;
  3. pdb檔案:包含了編譯後程式指向原始碼的位置資訊,用於除錯的時候定位原始碼,方便除錯;

我們把MyFirstApp.dll檔案通過ildasm中間語言工具開啟,可以看到這個程式的整個結構如下:

 然後雙擊main函式,可以看到該函式的中間語言表示如下:

四、執行過程

        第一步:我們上面的程式在編譯的時候,.NET會生成不依賴於作業系統和特定的CPU的中間語言,而中間語言

是可以在各個作業系統上都能編譯的程式碼,這種程式碼Java裡面叫做ByteCode(位元組碼),.NET

裡面我們稱之為MSIL指令(微軟中間語言)這是程式編譯的第一步。


        第二步:不管是Java的位元組碼還是.NET的MSIL指令是不能直接執行的,因為機器只能識別用0和1表示的機器語言

所以CLR裡面的JIT需要將上面的MSIL在一次編譯成CPU能夠執行的機器指令,最終由電腦執行。整個過程如下圖所示:

五、總結

         以上是本次分享的內容,有些地方可能不一定正確,歡迎大家批評指正

微信名片

作者 高紅斌
聯絡QQ 2358643757
出處 https://www.cnblogs.com/gaohongbin
本文版權歸作者和部落格園共有,如需全部轉載或者部分轉載、摘錄,請在文章明顯位置註明作者和原文連結。

相關文章