成人午夜视频全免费观看高清-秋霞福利视频一区二区三区-国产精品久久久久电影小说-亚洲不卡区三一区三区一区

深入淺析Java中的classloader與namespace-創(chuàng)新互聯(lián)

創(chuàng)新互聯(lián)www.cdcxhl.cn八線動態(tài)BGP香港云服務(wù)器提供商,新人活動買多久送多久,劃算不套路!

創(chuàng)新互聯(lián)是一家成都網(wǎng)站設(shè)計(jì)、成都網(wǎng)站建設(shè),提供網(wǎng)頁設(shè)計(jì),網(wǎng)站設(shè)計(jì),網(wǎng)站制作,建網(wǎng)站,按需定制,網(wǎng)站開發(fā)公司,于2013年開始是互聯(lián)行業(yè)建設(shè)者,服務(wù)者。以提升客戶品牌價(jià)值為核心業(yè)務(wù),全程參與項(xiàng)目的網(wǎng)站策劃設(shè)計(jì)制作,前端開發(fā),后臺程序制作以及后期項(xiàng)目運(yùn)營并提出專業(yè)建議和思路。

深入淺析Java中的 classloader與namespace?針對這個(gè)問題,這篇文章詳細(xì)介紹了相對應(yīng)的分析和解答,希望可以幫助更多想解決這個(gè)問題的小伙伴找到更簡單易行的方法。

Java classloader和namespace詳細(xì)介紹

  Java虛擬機(jī)通過裝載、連接和初始化一個(gè)JAVA類型,使該類型可以被正在運(yùn)行的JAVA程序所使用。其中,裝載就是把二進(jìn)制形式的JAVA類型讀入JAVA虛擬機(jī)中。連接就是把這種已經(jīng)讀入虛擬機(jī)的二進(jìn)制形式的類型數(shù)據(jù)合并到虛擬機(jī)的運(yùn)行時(shí)狀態(tài)中去。連接階段分為三個(gè)步驟-驗(yàn)證、準(zhǔn)備和解析。驗(yàn)證確保了JAVA類型數(shù)據(jù)格式正確并適于JAVA虛擬機(jī)使用。準(zhǔn)備負(fù)責(zé)為該類分配它所需的內(nèi)存,比如為它的類變量分配內(nèi)存。解析把常量池中的符號引用轉(zhuǎn)換為直接引用,如內(nèi)存地址指針。在初始化期間,激活類的靜態(tài)變量的初始化代碼和靜態(tài)代碼塊。

  裝載步驟的最終產(chǎn)品是一個(gè)被裝載類型的Class類的實(shí)例對象,它成為JAVA程序與內(nèi)部數(shù)據(jù)結(jié)構(gòu)之間的接口。對于每一個(gè)被裝載的類型,虛擬機(jī)都會相應(yīng)地為它創(chuàng)建一個(gè)Class類的實(shí)例。

1 類裝載器的安全作用

  JAVA類裝載器在JAVA安全體系結(jié)構(gòu)中起著最關(guān)重要的作用,是JAVA安全沙箱的第一道防線。類裝載器體系結(jié)構(gòu)在三個(gè)方面對JAVA的沙箱起作用:

1) 它防止惡意代碼去干涉善意的代碼
2) 它守護(hù)了被信任的類庫的邊界
3) 它將代碼歸入某類(稱為保護(hù)域),該類確定了代碼可以進(jìn)行哪些操作。

類裝載器體系結(jié)構(gòu)可以防止惡意代碼去干涉善意的代碼,這是通過為不同的類裝載器裝入的類提供不同的命名空間來實(shí)現(xiàn)的。

2雙親委派模型

  JAVA虛擬機(jī)規(guī)范定義了兩種類型的類裝載器-啟動類裝載器和用戶自定義類裝載器,啟動類裝載器是JAVA虛擬機(jī)實(shí)現(xiàn)的一部分,通過繼承ClassLoader類,用戶可以創(chuàng)建自定義的類裝載器來完成特定要求的加載。JAVA虛擬機(jī)已經(jīng)創(chuàng)建了2個(gè)自定義類裝載器-擴(kuò)展類裝載器和系統(tǒng)類裝載器。
每一個(gè)用戶自定義的類裝載器在創(chuàng)建時(shí)被分配一個(gè)“雙親”parent類裝載器。如果沒有顯示地傳遞一個(gè)雙親類裝載器給用戶自定義的類裝載器的構(gòu)造方法,系統(tǒng)類裝載器就默認(rèn)被指定為雙親。如果傳遞到構(gòu)造方法的是一個(gè)已有的用戶自定義類裝載器的引用,該用戶自定義類裝載器就作為雙親;如果向構(gòu)造方法傳遞了null,啟動類裝載器就是雙親。
啟動類裝載器Bootstrap Classloader:它是JAVA虛擬機(jī)實(shí)現(xiàn)的一部分,是c/c++實(shí)現(xiàn)的,它沒有雙親。啟動類裝載器裝載JAVA核心庫代碼。

擴(kuò)展類裝載器Extension Classloader:繼承自URLClassLoader,初始化向構(gòu)造方法傳遞了null,所以雙親是Bootstrap Classloaser。它從java.ext.dirs擴(kuò)展目錄中裝載代碼。

系統(tǒng)類裝載器Application Classloader:繼承自URLClassLoader,雙親是Extension Classloaser。它從CLASSPATH路徑中裝載應(yīng)用程序代碼。

其中,網(wǎng)絡(luò)類裝載器URLClassLoader是JAVA庫提供的一個(gè)類裝載器,用來從網(wǎng)絡(luò)其他位置裝載類。

深入淺析Java中的 classloader與namespace

雙親孩子類裝載器委派鏈

  在雙親委派模型下,當(dāng)一個(gè)裝載器被請求裝載某個(gè)類時(shí),它首先委托自己的雙親parent去裝載,若parent能裝載,則返回這個(gè)類所對應(yīng)的Class對象,若parent不能裝載,則由parent的請求者去裝載。

現(xiàn)在假設(shè)要求Cindy去裝載一個(gè)名為java.io.FileReader的類型。Cindy第一件事情就是去找Mom來裝載那個(gè)類型;Mom所做的第一件事情就是去找Grandma來裝載那個(gè)類型;而Grandma首先去找啟動類裝載器去裝載。在這個(gè)例子中,啟動類裝載器可以裝載那個(gè)類型,它就返回代表java.io.FileReader的Class實(shí)例給Grandma。Grandma傳遞該Class的引用 Mom,Mom再回傳給Cindy,Cindy返回給程序。

 深入淺析Java中的 classloader與namespace

  在此模型下,啟動類裝載器可以搶在擴(kuò)展類裝載器之前去裝載類,而擴(kuò)展類裝載器可以搶在系統(tǒng)類裝載器之前去裝載那個(gè)類,系統(tǒng)類裝載器又可以搶在網(wǎng)絡(luò)類裝載器之前去裝載它。這樣,使用雙親-孩子委派鏈的方式,啟動類裝載器會在最可信的類庫-核心Java API-中首先檢查每個(gè)被裝載的類型,然后,才依次到擴(kuò)展路徑、系統(tǒng)類路徑中檢查被裝載的類型文件。用這種方法,類裝載器的體系結(jié)構(gòu)就可以防止不可靠的代碼用它們自己的版本來替代可以信任的類。

3命名空間

由不同的類裝載器裝載的類將被放在虛擬機(jī)內(nèi)部的不同命名空間。命名空間由一系列唯一的名稱組成,每一個(gè)被裝載的類有一個(gè)名字。JAVA虛擬機(jī)為每一個(gè)類裝載器維護(hù)一個(gè)名字空間。例如,一旦JAVA虛擬機(jī)將一個(gè)名為Volcano的類裝入一個(gè)特定的命名空間,它就不能再裝載名為Valcano的其他類到相同的命名空間了??梢园讯鄠€(gè)Valcano類裝入一個(gè)JAVA虛擬機(jī)中,因?yàn)榭梢酝ㄟ^創(chuàng)建多個(gè)類裝載器從而在一個(gè)JAVA應(yīng)用程序中創(chuàng)建多個(gè)命名空間。

1)  初始類裝載器/ 定義類裝載器

命名空間有助于安全的實(shí)現(xiàn),因?yàn)槟憧梢杂行У卦谘b入了不同命名空間的類之間設(shè)置一個(gè)防護(hù)罩。在JAVA虛擬機(jī)中,在同一個(gè)命名空間內(nèi)的類可以直接進(jìn)行交互,而不同的命名空間中的類甚至不能覺察彼此的存在,除非顯示地提供了允許它們進(jìn)行交互的機(jī)制,如獲取Class對象的引用后使用反射來訪問。

  如果要求某個(gè)類裝載器去裝載一個(gè)類型,但是卻返回了其他類裝載器裝載的類型,這種裝載器被稱為是那個(gè)類型的初始類裝載器 ;而實(shí)際裝載那個(gè)類型的類裝載器被稱為該類型的定義類裝載器 。任何被要求裝載類型,并且能夠返回Class實(shí)例的引用代表這個(gè)類型的類裝載器,都是這個(gè)類型的初始類裝載器。在上面的一個(gè)例子中,java.io.FileReader定義類裝載器是啟動類裝載器,Cindy、Mom、Grandma、啟動類裝載器都是初始類裝載器。

  虛擬機(jī)會為每一個(gè)類裝載器維護(hù)一張列表,列表中是已經(jīng)被請求過的類型的名字。這些列表包含了每一個(gè)類裝載器被標(biāo)記為初始類裝載器的類型,它們代表了每一個(gè)類裝載器的命名空間。虛擬機(jī)總是會在調(diào)用loadClass()之前檢查這個(gè)內(nèi)部列表,如果這個(gè)類裝載器已經(jīng)被標(biāo)記為是這個(gè)具有該全限定名的類型的初始類裝載器,就會返回表示這個(gè)類型的Class實(shí)例,這樣,虛擬機(jī)永遠(yuǎn)不會自動在同一個(gè)用戶自定義類裝載器上調(diào)用同一個(gè)名字的類型兩次。

2) 命名空間的類型共享

  前面提到過只有同一個(gè)命名空間內(nèi)的類才可以直接進(jìn)行交互,但是我們經(jīng)常在由用戶自定義類裝載器定義的類型中直接使用Java API類,這不是矛盾了嗎?這是類型共享 原因-如果某個(gè)類裝載器把類型裝載的任務(wù)委派給另外一個(gè)類裝載器,而后者定義了這個(gè)類型,那么被委派的類裝載器裝載的這個(gè)類型,在所有被標(biāo)記為該類型的初始類裝載器的命名空間中共享。
例如上面的例子中,Cindy可以共享Mon、Grandma、啟動類裝載器的命名空間中的類型,Kenny也可以共享 Mon、Grandma、啟動類裝載器的 命名空間中的 類型,但是Cindy和Kenny的命名空間不能共享。

3) 運(yùn)行時(shí)包

  每個(gè)類裝載器都有自己的命名空間,其中維護(hù)著由它裝載的類型。所以一個(gè)JAVA程序可以多次裝載具有同一個(gè)全限定名的多個(gè)類型。這樣一個(gè)類型的全限定名就不足以確定在一個(gè)JAVA虛擬機(jī)中的唯一性。因此,當(dāng)多個(gè)類裝載器都裝載了同名的類型時(shí),為了唯一表示該類型,還要在類型名稱前加上裝載該類型的類裝載器來表示-[classloader class]。
  在允許兩個(gè)類型之間對包內(nèi)可見的成員進(jìn)行訪問前,虛擬機(jī)不但要確定這個(gè)兩個(gè)類型屬于同一個(gè)包,還必須確認(rèn)它們屬于同一個(gè)運(yùn)行時(shí)包-它們必須有同一個(gè)類裝載器裝載的。這樣,java.lang.Virus和來自核心的java.lang的類不屬于同一個(gè)運(yùn)行時(shí)包,java.lang.Virus就不能訪問JAVA API的java.lang包中的包內(nèi)可見的成員。

4自定義類裝載器

  JAVA類型要么由啟動類裝載器裝載,要么通過用戶自定義的類裝載器裝載。啟動類裝載器是虛擬機(jī)實(shí)現(xiàn)的一部分,它以與實(shí)現(xiàn)無關(guān)的方式裝載類型,JAVA提供了抽象類java.lang.ClassLoader,用戶自定義的類裝載器是類ClassLoader的子類實(shí)例,它以定制的方式裝載類。所有用戶自定義類裝載器都實(shí)例化自ClassLoader的子類。
下面提供一個(gè)簡單的用戶自定義類裝載器。

import java.io.*; 
public class UserDefinedClassLoader extends ClassLoader 
{ 
 private String directory = "d:/classes/"; 
 private String extensionType = ".class"; 
  
 public UserDefinedClassLoader() 
 { 
  super(); // this set the parent as the AppClassLoader by default 
 } 
  
 public UserDefinedClassLoader( ClassLoader parent ) 
 { 
  super( parent ); 
 } 
  
 public Class findClass( String name ) 
 { 
  byte[] data = loadClassData( name ); 
   
  return defineClass( name, data, 0, data.length ); 
 } 
  
 private byte[] loadClassData( String name ) 
 { 
  byte[] data = null; 
  try 
  { 
   FileInputStream in = new FileInputStream( new File( directory + name.replace( '.', '/') + extensionType ) ); 
   ByteArrayOutputStream out = new ByteArrayOutputStream(); 
   int ch = 0; 
    
   while( ( ch = in.read() ) != -1 ) 
   { 
    out.write( ch ); 
   } 
    
   data = out.toByteArray(); 
  } 
  catch ( IOException e ) 
  { 
   e.printStackTrace(); 
  } 
  return data; 
 } 
} 
 

分享題目:深入淺析Java中的classloader與namespace-創(chuàng)新互聯(lián)
標(biāo)題網(wǎng)址:http://jinyejixie.com/article38/djcgsp.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供靜態(tài)網(wǎng)站網(wǎng)站收錄、網(wǎng)站策劃云服務(wù)器、網(wǎng)站導(dǎo)航、品牌網(wǎng)站制作

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時(shí)間刪除。文章觀點(diǎn)不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時(shí)需注明來源: 創(chuàng)新互聯(lián)

手機(jī)網(wǎng)站建設(shè)
临海市| 桐柏县| 巫山县| 垫江县| 霍林郭勒市| 壤塘县| 无为县| 泽库县| 邛崃市| 婺源县| 报价| 文昌市| 米易县| 克东县| 昭通市| 永川市| 涡阳县| 万盛区| 册亨县| 五常市| 龙海市| 定安县| 德钦县| 保亭| 芮城县| 名山县| 北流市| 巫山县| 平武县| 清远市| 泰兴市| 江源县| 时尚| 定州市| 康马县| 西林县| 漳州市| 五家渠市| 娄烦县| 扎囊县| 依安县|