<rt id="bn8ez"></rt>
<label id="bn8ez"></label>

  • <span id="bn8ez"></span>

    <label id="bn8ez"><meter id="bn8ez"></meter></label>

    Flyingis

    Talking and thinking freely !
    Flying in the world of GIS !
    隨筆 - 156, 文章 - 16, 評(píng)論 - 589, 引用 - 0
    數(shù)據(jù)加載中……

    淺議類(lèi)型識(shí)別與反射機(jī)制

        作者:Flyingis

        運(yùn)行時(shí)類(lèi)型識(shí)別
    (Run-time Type Identification, RTTI)主要有兩種方式,一種是我們?cè)诰幾g時(shí)和運(yùn)行時(shí)已經(jīng)知道了所有的類(lèi)型,另外一種是功能強(qiáng)大的“反射”機(jī)制。

           要理解RTTIJava中的工作原理,首先必須知道類(lèi)型信息在運(yùn)行時(shí)是如何表示的,這項(xiàng)工作是由“Class對(duì)象”完成的,它包含了與類(lèi)有關(guān)的信息。類(lèi)是程序的重要組成部分,每個(gè)類(lèi)都有一個(gè)Class對(duì)象,每當(dāng)編寫(xiě)并編譯了一個(gè)新類(lèi)就會(huì)產(chǎn)生一個(gè)Class對(duì)象,它被保存在一個(gè)同名的.class文件中。在運(yùn)行時(shí),當(dāng)我們想生成這個(gè)類(lèi)的對(duì)象時(shí),運(yùn)行這個(gè)程序的Java虛擬機(jī)(JVM)會(huì)確認(rèn)這個(gè)類(lèi)的Class對(duì)象是否已經(jīng)加載,如果尚未加載,JVM就會(huì)根據(jù)類(lèi)名查找.class文件,并將其載入,一旦這個(gè)類(lèi)的Class對(duì)象被載入內(nèi)存,它就被用來(lái)創(chuàng)建這個(gè)類(lèi)的所有對(duì)象。一般的RTTI形式包括三種:

    1.       傳統(tǒng)的類(lèi)型轉(zhuǎn)換。如“(Apple)Fruit”,由RTTI確保類(lèi)型轉(zhuǎn)換的正確性,如果執(zhí)行了一個(gè)錯(cuò)誤的類(lèi)型轉(zhuǎn)換,就會(huì)拋出一個(gè)ClassCastException異常。

    2.       通過(guò)Class對(duì)象來(lái)獲取對(duì)象的類(lèi)型。如

    Class c = Class.forName(“Apple”);

    Object o = c.newInstance();

    3.       通過(guò)關(guān)鍵字instanceofClass.isInstance()方法來(lái)確定對(duì)象是否屬于某個(gè)特定類(lèi)型的實(shí)例,準(zhǔn)確的說(shuō),應(yīng)該是instanceof / Class.isInstance()可以用來(lái)確定對(duì)象是否屬于某個(gè)特定類(lèi)及其所有基類(lèi)的實(shí)例,這和equals() / ==不一樣,它們用來(lái)比較兩個(gè)對(duì)象是否屬于同一個(gè)類(lèi)的實(shí)例,沒(méi)有考慮繼承關(guān)系。

     

    反射

           如果不知道某個(gè)對(duì)象的類(lèi)型,可以通過(guò)RTTI來(lái)獲取,但前提是這個(gè)類(lèi)型在編譯時(shí)必須已知,這樣才能使用RTTI來(lái)識(shí)別。即在編譯時(shí),編譯器必須知道所有通過(guò)RTTI來(lái)處理的類(lèi)。

    使用反射機(jī)制可以不受這個(gè)限制,它主要應(yīng)用于兩種情況,第一個(gè)是“基于構(gòu)件的編程”,在這種編程方式中,將使用某種基于快速應(yīng)用開(kāi)發(fā)(RAD)的應(yīng)用構(gòu)建工具來(lái)構(gòu)建項(xiàng)目。這是現(xiàn)在最常見(jiàn)的可視化編程方法,通過(guò)代表不同組件的圖標(biāo)拖動(dòng)到圖板上來(lái)創(chuàng)建程序,然后設(shè)置構(gòu)件的屬性值來(lái)配置它們。這種配置要求構(gòu)件都是可實(shí)例化的,并且要暴露其部分信息,使得程序員可以讀取和設(shè)置構(gòu)件的值。當(dāng)處理GUI時(shí)間的構(gòu)件時(shí)還必須暴露相關(guān)方法的細(xì)細(xì),以便RAD環(huán)境幫助程序員覆蓋這些處理事件的方法。在這里,就要用到反射的機(jī)制來(lái)檢查可用的方法并返回方法名。Java通過(guò)JavaBeans提供了基于構(gòu)件的編程架構(gòu)。

           第二種情況,在運(yùn)行時(shí)獲取類(lèi)的信息的另外一個(gè)動(dòng)機(jī),就是希望能夠提供在跨網(wǎng)絡(luò)的遠(yuǎn)程平臺(tái)上創(chuàng)建和運(yùn)行對(duì)象的能力。這被成為遠(yuǎn)程調(diào)用(RMI),它允許一個(gè)Java程序?qū)?duì)象分步在多臺(tái)機(jī)器上,這種分步能力將幫助開(kāi)發(fā)人員執(zhí)行一些需要進(jìn)行大量計(jì)算的任務(wù),充分利用計(jì)算機(jī)資源,提高運(yùn)行速度。

           Class支持反射,java.lang.reflect中包含了Field/Method/Constructor類(lèi),每個(gè)類(lèi)都實(shí)現(xiàn)了Member接口。這些類(lèi)型的對(duì)象都是由JVM在運(yùn)行時(shí)創(chuàng)建的,用來(lái)表示未知類(lèi)里對(duì)應(yīng)的成員。如可以用Constructor類(lèi)創(chuàng)建新的對(duì)象,用get()set()方法讀取和修改與Field對(duì)象關(guān)聯(lián)的字段,用invoke()方法調(diào)用與Method對(duì)象關(guān)聯(lián)的方法。同時(shí),還可以調(diào)用getFields()getMethods()getConstructors()等方法來(lái)返回表示字段、方法以及構(gòu)造器的對(duì)象數(shù)組。這樣,未知的對(duì)象的類(lèi)信息在運(yùn)行時(shí)就能被完全確定下來(lái),而在編譯時(shí)不需要知道任何信息。

           另外,RTTI有時(shí)能解決效率問(wèn)題。當(dāng)程序中使用多態(tài)給程序的運(yùn)行帶來(lái)負(fù)擔(dān)的時(shí)候,可以使用RTTI編寫(xiě)一段代碼來(lái)提高效率。

    Happy Birthday to myself!

    posted on 2005-12-11 14:43 Flyingis 閱讀(2261) 評(píng)論(9)  編輯  收藏 所屬分類(lèi): JavaSE

    評(píng)論

    # re: 淺議類(lèi)型識(shí)別與反射機(jī)制  回復(fù)  更多評(píng)論   

    Happy birthday to you and wish you have a nice day! Enjoy yourself!
    2005-12-11 16:31 | 非魚(yú)

    # re: 淺議類(lèi)型識(shí)別與反射機(jī)制  回復(fù)  更多評(píng)論   

    Thanks:)
    2005-12-11 17:10 | Flyingis

    # re: 淺議類(lèi)型識(shí)別與反射機(jī)制  回復(fù)  更多評(píng)論   

    Happy Birthday to you.
    2005-12-12 07:45 | licl

    # re: 淺議類(lèi)型識(shí)別與反射機(jī)制  回復(fù)  更多評(píng)論   

    糾正一點(diǎn)錯(cuò)誤觀點(diǎn),RTTI 會(huì)帶來(lái)效率問(wèn)題,其效率遠(yuǎn)低于多態(tài),相差可達(dá)2到3個(gè)數(shù)量級(jí)。

    多態(tài),如 接口,重載。其效率除了靜態(tài)方法外是最高的。
    事實(shí)上多態(tài)涉及到了絕對(duì)多數(shù)的代碼:Java代碼中除了靜態(tài)方法和標(biāo)記了 final 的方法(?,待做試驗(yàn))外,所有的普通方法全部是虛方法(多態(tài))調(diào)用。

    祝你生日快樂(lè)。
    2005-12-12 13:46 | 笨笨

    # re: 淺議類(lèi)型識(shí)別與反射機(jī)制  回復(fù)  更多評(píng)論   

    今年是本命年,謝謝各位!
    ----------
    笨笨的分析讓我學(xué)習(xí)不少。但是,在任何情況下RTTI的效率都會(huì)低于多態(tài)嗎?當(dāng)在某種環(huán)境下多態(tài)產(chǎn)生了低效率時(shí),采用RTTI是否是一種可行的解決方式?
    2005-12-12 15:20 | Flyingis

    # re: 淺議類(lèi)型識(shí)別與反射機(jī)制  回復(fù)  更多評(píng)論   

    多態(tài)就是普通的Java 方法調(diào)用,效率不會(huì)低的。
    如果效率低,只能說(shuō):考慮改進(jìn)算法或換JNI實(shí)現(xiàn)。
    2005-12-12 17:43 | 笨笨

    # re: 淺議類(lèi)型識(shí)別與反射機(jī)制  回復(fù)  更多評(píng)論   

    THINKING IN JAVA中的東西。剛接觸的人STILL FAINT。。。
    2006-06-28 11:24 | Against

    # re: 淺議類(lèi)型識(shí)別與反射機(jī)制  回復(fù)  更多評(píng)論   

    /*
    例,這和equals() / ==不一樣,它們用來(lái)比較兩個(gè)對(duì)象是否屬于同一個(gè)類(lèi)的實(shí)例,沒(méi)有考慮繼承關(guān)系。
    */
    這句話有誤.
    2006-12-26 12:52 | John[匿名]

    # re: 淺議類(lèi)型識(shí)別與反射機(jī)制  回復(fù)  更多評(píng)論   

    @John[匿名]
    謝謝提示,以前理解錯(cuò)了。
    一個(gè)是值的比較,一個(gè)是內(nèi)存地址比較。
    2006-12-28 16:21 | Flyingis
    主站蜘蛛池模板: 亚洲高清在线观看| 成人免费午夜在线观看| 成人国产网站v片免费观看| 亚洲最大的成人网| 亚洲av极品无码专区在线观看| 久久精品国产亚洲av水果派| 亚洲国产老鸭窝一区二区三区| 亚洲av午夜福利精品一区| 国产亚洲美女精品久久久久狼| 亚洲精品中文字幕无码蜜桃 | 一级中文字幕免费乱码专区 | 久久久久亚洲AV成人无码| 亚洲国产精品成人精品无码区在线 | 免费又黄又爽又猛大片午夜 | 亚洲小视频在线观看| 久久水蜜桃亚洲av无码精品麻豆| 伊人久久综在合线亚洲2019| 亚洲精品日韩专区silk| 亚洲国产精品免费在线观看| 亚洲男人天堂2018av| 亚洲爆乳无码专区www| 猫咪免费人成网站在线观看入口| 人成午夜免费大片在线观看| 国产精品美女免费视频观看| 国产日韩AV免费无码一区二区| 国产午夜精品久久久久免费视 | 美女被免费视频网站| 亚洲视频在线免费| 先锋影音资源片午夜在线观看视频免费播放 | 亚洲午夜久久久精品影院| 国产精品亚洲精品观看不卡| 老司机亚洲精品影院在线观看| 免费在线观看一区| 人人玩人人添人人澡免费| 成人免费黄色网址| 免费观看国产小粉嫩喷水| 中文字幕日韩亚洲| 亚洲美女在线观看播放| 亚洲爆乳成av人在线视菜奈实| 国产黄在线播放免费观看| 久久国产乱子伦精品免费不卡|