From 4493a11de2986fcf5b08aca6c581d6ab339e66fb Mon Sep 17 00:00:00 2001 From: Moilk Date: Tue, 9 Apr 2019 19:07:59 +0800 Subject: [PATCH 1/2] =?UTF-8?q?=E5=AE=8C=E6=88=90=E7=AC=AC19=E7=AB=A0?= =?UTF-8?q?=E7=AC=AC1=E8=8A=82?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 6 ++ docs/book/19-Type-Information.md | 77 +++++++++++++++++- .../image-20190409114913825-4781754.png | Bin 0 -> 38151 bytes 3 files changed, 81 insertions(+), 2 deletions(-) create mode 100644 docs/images/image-20190409114913825-4781754.png diff --git a/.gitignore b/.gitignore index 4cb12d8..6d3e913 100644 --- a/.gitignore +++ b/.gitignore @@ -14,3 +14,9 @@ _book *.epub *.mobi *.pdf + +# OSX junk files +.DS_Store +._* +*/.DS_Store +*/._* diff --git a/docs/book/19-Type-Information.md b/docs/book/19-Type-Information.md index 8f38ac8..e2e8f79 100644 --- a/docs/book/19-Type-Information.md +++ b/docs/book/19-Type-Information.md @@ -3,16 +3,89 @@ # 第十九章 类型信息 +> RTTI(RunTime Type Information, 运行时类型信息)能够在程序运行时发现和使用类型信息 + +RTTI把我们从只能在编译期进行面向类型操作的禁锢中解脱了出来,并且让我们可以使用某些非常强大的程序。对RTTI的需要,揭示了面向对象设计中许多有趣(并且复杂)的特性,同时也带来了关于如何组织程序的基本问题。 + +本章将讨论Java是如何在运行时识别对象和类信息的。主要有两种方式: + +1. “传统的” RTTI:假定我们在编译时已经知道了所有的类型; +2. “反射”机制:允许我们在运行时发现和使用类的信息。 -## 运行时类型信息 +## 为什么需要RTTI + +下面看一下我们已经很熟悉的一个例子,它使用了多态的类层次结构。基类`Shape`是泛化的类型,从它派生出了三个具体类: `Circle` 、`Square` 和 `Triangle` (见下图所示)。 + +![多态例子Shape的类层次结构图](../images/image-20190409114913825-4781754.png) + +这是一个典型的类层次结构图,基类位于顶部,派生类向下扩展。面向对象编程的一个基本目的是:让代码只操纵对基类(这里即 `Shape` )的引用。这样,如果你想添加一个新类(比如从`Shape`派生出`Rhomboid`)来扩展程序,就不会影响原来的代码。在这个例子中,`Shape`接口中动态绑定了`draw()`方法,这样做的目的就是让客户端程序员可以使用泛化的`Shape`引用来调用`draw()`。`draw()`方法在所有派生类里都会被覆盖,而且由于它是动态绑定的,所以它可以使用`Shape`引用来调用,这就是多态。 + +因此,我们通常会创建一个具体的对象(`Circle`、`Square` 或者`Triangle`),把它向上转型成`Shape`(忽略对象的具体类型),并且在后面的程序中使用`Shape`引用来调用在具体对象中被重载的方法(如`draw()`)。 + +代码如下: + +```java +// typeinfo/Shapes.java +import java.util.stream.*; + +abstract class Shape { + void draw() { System.out.println(this + ".draw()"); } + @Override + public abstract String toString(); +} + +class Circle extends Shape { + @Override + public String toString() { return "Circle"; } +} + +class Square extends Shape { + @Override + public String toString() { return "Square"; } +} + +class Triangle extends Shape { + @Override + public String toString() { return "Triangle"; } +} + +public class Shapes { + public static void main(String[] args) { + Stream.of( + new Circle(), new Square(), new Triangle()) + .forEach(Shape::draw); + } +} +/* Output: +Circle.draw() +Square.draw() +Triangle.draw() +*/ +``` + +基类中包含`draw()`方法,它通过传递`this`参数传递给`System.out.println()`,间接地使用`toString()`打印类标识符(注意:这里将`toString()`声明为了`abstract`,以此强制继承者覆盖改方法,并防止对`Shape`的实例化)。如果某个对象出现在字符串表达式中(涉及"+"和字符串对象的表达式),`toString()`方法就会被自动调用,以生成表示该对象的`String`。每个派生类都要覆盖(从`Object`继承来的)`toString()`方法,这样`draw()`在不同情况下就打印出不同的消息(多态)。 + +这个例子中,在把`Shape`对象放入`Stream`中时就会进行向上转型(隐式),但在向上转型的时候也丢失了这些对象的具体类型。对`steam`而言,它们只是`Shape`对象。 + +严格来说,`Stream`实际上是把放入其中的所有对象都当做`Object`对象来持有,只是取元素时会自动将其类型转为`Shape`。这也是 RTTI 最基本的使用形式,因为在 Java 中,所有类型转换的正确性检查都是在运行时进行的。这也正是 RTTI 的含义所在:在运行时,识别一个对象的类型。 + +另外在这个例子中,类型转换并不彻底:`Object`被转型为`Shape`,而不是`Circle`、`Square`或者`Triangle`。这是因为目前我们只能确保这个 `Stream`保存的都是`Shape`: + +- 编译期,`stream`和 Java 泛型系统确保放入`stream`的都是`Shape`对象(`Shape`子类的对象也可视为`Shape`的对象),否则编译器会报错; +- 运行时,自动类型转换确保了从`stream`中取出的对象都是`Shape`类型。 + +接下来就是多态机制的事了,`Shape`对象实际执行什么样的代码,是由引用所指向的具体对象(`Circle`、`Square`或者`Triangle`)决定的。这也符合我们编写代码的一般需求,通常,我们希望大部分代码尽可能少了解对象的具体类型,而是只与对象家族中的一个通用表示打交道(本例中即为`Shape`)。这样,代码会更容易写,更易读和维护;设计也更容易实现,更易于理解和修改。所以多态是面向对象的基本目标。 + +但是,有时你会碰到一些编程问题,在这些问题中如果你能知道某个泛化引用的具体类型,就可以把问题轻松解决。例如,假设我们允许用户将某些几何形状高亮显示,现在希望找到屏幕上所有高亮显示的三角形;或者,我们现在需要旋转所有图形,但是想跳过圆形(因为圆形旋转没有意义)。这时我们就希望知道`Stream`里边的形状具体是什么类型,而Java 实际上也满足了我们的这种需求。使用 RTTI,我们可以查询某个`Shape`引用所指向对象的确切类型,然后选择或者剔除特例。 -## 类的对象 +## Class对象 + ## 类型转换检测 diff --git a/docs/images/image-20190409114913825-4781754.png b/docs/images/image-20190409114913825-4781754.png new file mode 100644 index 0000000000000000000000000000000000000000..0edbfec7c20615cdd8d1bd16b254c332d06b3cb5 GIT binary patch literal 38151 zcmeFYWm{a$wl<2>xVt++8+RuVf`x?O(zt7IcXxtYf(N(Y?(PH#1b0Gkm%Ou|v-Y$0 zZ#dWH3s=vsnq4(&=soU=e5WFhfl7)B0|SGh@J9AM3=A9=3=Aw52nl#HFu^1N1A|&+ zB_s1rK}Lr9owI|vm8}^J%$vxRRAlvJZNj1T+aduS>RA*%d?{hr!o}&L;MfEN5JN}^ zHLaU0;!sc&sFaRBD#!%Zlr4gpP_`z(R}u-C)w<|O1i+ATF-V$y>X&XxNPr2jyt#Mx{Vhj} z^NS~E^!l{xuja@nPh(7&cc9*LJuW7UO`eGFjv@Iid z@GP2LqqZ&XHeHlFN|Af%U^Yf<8<}xnW(BuOESzu?MNQ2@CJ^;HVT=qza)cCYIeN3O zbF)%Y#RuMCbc0_wJ#qi0@)%?$PpEvpP~x2H^}ZPBRlm9Tdnx$RH2a>R-ur-7P6hWq zj8-+{+b2bZ+q61rab}Oy`_;ocE0v@>xp8j!-#8*;dW|JrE_T-My4je{I<#j+Gb+xs z35&wtUS9Sa7}bvxJ})UI;chbiN*hYr8&^P$&)jA6Go5CO{?Pm6-|z9}nO32+VGkj( zsbPrs-0)$mzVJLlVY73Va#_N9JF=jN&(Sm2;C&ahG%4Mz{h?W+87paipBCxY}cEAQZ zWXthucD0u>;G4JLr9fAS@;YaP+hsT>$>Hh`6qu#m@OW>sfG~8J9VNdz;sF?D>TA9x zNBaB<5-P7FH24TfLS{IEFOlu?Vcq!OrU?b%G&c~RB*7qLE(pp-0DS_IEQDkj(MC#~ z8DXWz{v9f2fXo-%Y?u;BctI?VV4DrX0|cyYylFI~ZW}PFcn}IG$PpVcUz#O>un;Rl zG8G%oIjsE)3^RUI;MNz}H!uoc^en~HK?G7o(^93V4~W9Z`eF8x`qOl!SfpWVQic$G zr7!{`j3t;{WF8}dB`VBtqP|E+q-^;89^FmcW;k)o#lEyn-81-RB0r4yuP{*|`Cl8< zikTTl;R#}*UNd}=E&W&ur_NOd_c7X9`uo>EU%k}mN~bK@GNXzMlxN~B4P6j2gC`}c zr5&Ww@>yrD4>YdCT&TS8pDAQ|N==l&n8bvPq{$K5VIxEMCUM4-##P3Y5F{{Ftri=` zSocpO-&(FE)8DAS34e>*QZ$mRgq{q=Z8{1PWTQ-?5XG2mb35HPcQkJ|D>k<^!>$VE zhAj5#Zgrg3dcgWobP^lJc13hWQ}wH2?|>c*n>X1Egw58YHip$wE zO3-$dykkbf*L=&ykX)DY{&kDArwU2h*U|Km8q;R(aBeOrF?THM-M`Nuc9ElT& z?5Sex-tum;anu&n`!qwTx(u3(?kZLC_DZ=d4m4D3d5m4JJ9S>do)X|xdL(-k1IrUi z9N%n4NlOsCUMTW--DaVIj)m|T6WtG(?)M5)XzPPMhCJ76?5O_Jc||Q&5jrk{><9VP%O;NqRo#jl+Soqs7_lPF&&=HIL!Su?FL71 zFIi4Q!2R#cYlwwnNC!X2M174m3Ns4b^rfr7nPVQX%u_4jvb8nIHq|rt8A9N%<=f2q z&2yL;ona%P32rjBkAJm1KfycJFxW5^V@?QZoUG{iJt5lRS$pX=Zj*KUYjsd`;i={x z4-FAbBHEQunedb?mR%^-EcLdMSz}G3ypptXO(#q1vf@@(qT%aLgrBwzR<-x$HWsXP zmES2E=jx;DS(}cHSh!`qIO#MgA#&Sl*;b>^qG!;2)atAs--_8v(!$V2;qJX{|A)g_;`n8x zug9cFzMg4xZm7PyzE81-wYPl!xTPu1J>Na{wlqF=3N_E%Fs8ce6my+26)C!}%sBR8 z`M&bX=9=j-{66iW3k1f*M&w284fG2XfzLxaL`DfB4Uz)0dRUy*W6Qmf8?HvHL6au@ z%Yvs2~E)~tu8G$uCM>~z{eq9 zGvs>KC6n`tyNf%uIAjZ~eZIw%wrG*@Pg?}%NO;+}QMh5aIk@hOm`pA71Wd7KVs}MP zO(UHn$Vn1K2qol-8A`ElD;4`n28wdFe!DdKG*Y+uwwzx~j3Iw&{}fjtS-nwVIkGUR zpS997Yq#6;ak}j8BYU~4=6)rm)^>fdGrN=B=+Bko@kN5l#~N{K-w(NRYnkmY7~*8s z7iJf)@5RU{1Spq6*811yYnQDr*Cy7{nh^!iCeWhMy6iV?TkewwR2d|c?Uk2))=s#s zyqqkZ1fBd6(Q{KL93k4pzdl7@)$WS!EQc(H|59{cXKv&WuL*CKuPbSy|5E5wy|#AZ z-IdCiBF_AYvz%3vb6xMnipqWc*K^gQ4VEQ2v*_8b#mf{H)&qG(HMo>nJVflX>%s2k zaG#xgx_nt&86~^u!%6yvmV=q4nN5oR$B*B=t{X|4<=*r7_{^M7;^i`t+9=y#{g^pI zRSil`O0M>cd@OqW{P$bx-1yvgi>s;6c}2PGrQt_ui}C#Qd{_K~yly#{B8#&-OD;E> z^@i~|i{gfEQir{b(f!e$L`qYa?%xPOfLWt}55R?o`Hly()te#YsWUxp zE1|q0aX!u_#;yw!R{=}iOAwG?4s%0i9*|CM{9*fDGiyL)Md6KVBwhuZg>z!!Ar6nY z(7gdXj2<4$x@>YX-XkMZ7lmAuZ^$?o3D4#IXE>$AmK8DnA9GJ@$<;R9T?bU}bUYovtv!P{ZLx^uypnFpU#r-{V)C>h{#p>!>y`lzdHf?0ST?h7Smh8So zen3s55+52IZ1{`tKCl~14HidFi4jJEvjaic+Ru8?tWMWDc1;7g0!^GDNgyInKmbXG zxh02A19PQ*8^6B)^R?A-of+(VYA`P-SrMWq1dgW^%kjJjPN?<50d`_xFE@?z)R^@VUPT#gd)}V>4rewrN^>6KE3L z51*VbGkB5@i_#2~ro{*9r{bf~S*LwXT4|3;_IG_pdFO<6vk^6TO- zfv%odPjm=ks3b8KTA5G*_X!Bxoc9VH-T^yXVJMzTl}ROgx*pSFGUlKRzAl{&%yH2V z!?0RI3$Y*{KQk4uadxJq5O#T|QK4eh6}8RP_fsUSdaX7?#K%s&pN~Jd=Lr>+?CNCX zeFajQ79w3k0M3_@6YEk&xnL5^D?AajWS}VFHAQ_-T_cGTkrIyhvqr752d9)Vq+Op& zTs&8!QYR%<&rym-R)f;mn3#O}e)3hLS@m9VHMxiz+sR6kss@G1@u<3$jXR2Q#SMJGryw*w<+#Z88p>!&kEeN(yznSI*3nO^beOV?X#kPb*Bbn!x@R9BYXg}n<9YmFXX?L znz`m1m~hi5sW?Ko%|k<1ksIulUT{lwT2Xg9snNH<)E5#b?6_%D8ANiS-2Hiy5D-+_ zAX1^SC8|JMQLxa?M`U!=Hb$ne`;i4*g&XPBAeU-Umml=E@G;@GY^5`io7%*9IjcBm z2!#A_wc1TJD+1O;AOtvg+HSS*o(b7aHX=r(DZVc(J%pffPXyy#qe%fZW)A}#NL+&a z`{Hm%Gz!>SBrvG3*4I0YUs~Ju{YlV4i()bG3N+F{FeRbOrQEK0T!0e#MVB{RM$1kD zcnCW|F4d&&-VDtG>&o6coqU_TT%{Bbl&y@=>mitR5cV4}Q1W!dL`t2LMU8se2&q}l zK>}?#k+lXLAq*){@bVuU#Xx`yJfwzL&=}ua2_L-94ULkl5M`TBjrDS+=}zK}YvK@k zwSE}#hFeoifkYu)m*ekGrt6VbzJ-xBa8c{8%^P99UPnx7%f%x$78tqNyIq0&sF!?( z3l^jRkKNA_c%t`g*2MYnfkMH6%6%$+C7oCw3A63Tcd?Hp`Ehp_>q-5be3nTi!|7gg zxAId?SF-@&k&(D@NNu-#%($8NE4swv4@D&L_l_hbGn1j~x&`%yt)!SbF$=2=BbG}| z6fDYb($<_hyUXw+-%&eG0!p-*EklWzYlC3Ra-hlKbK`9BkKIPf7AO&ysT^Q8eV_QUz*kP&Oy@1Pq7e zTLL8w5i-%kCY6@o4YQ&WBR94tG_mdUXvumMeAW8~E-(0?*AEvcNsUbm0uC7|=v6vg zU`u$w%TWm%NBT@am^rg)=F?iiQ@@85xcRC@Giw@fiU@mnfPRmc{6N)*55$GlAlq># z+#!;>zjus5j6tb7au;UocdV(z;Gwl;E%;j|r#;^Qr!m>UEnf`$Q2I91QisTx=g|;a zaUfg!;cZ&l#L6~{Rmy4lZrVDHw%VjrfOAyMRYJz1R1$IjqfTYA6@->rxKO@W+U0$l z>$0%{d;fhp(tf618l}%j1AwY39Kff!+grUv4F6x*2RCm323H#i=vl3krLb>GPmmA!f zX6RyMaf5k@Sb0gn{cP}Eg`aRb{GGx5@F}}wU{&46Fk;dEUpA_6?7D%!4E8RB;veGL{EvB(Ob%y@k{TO;I*q$yQ}S;75QR@V{eWqQsdP#yopNi;I@~rX!uoy; zS?P)xrWHSE&=_=fxj@X75$vLnK2Fu}ajjSMU4c|3(!G_<$k5xjq$%9I!HeKt=+e@l zUWMbk+yO2~2{v${TyrdSzDfsQ3-NApJG^I66eQ@vhC=j2@8dajK67;Jyw|UlWSGSw7yP12 zTfxYd>e8s7wb@PF3`Fk*W}~*9?!aK$+lHM{hroAx`L7jcM^jkmwg#d<#&>w%78S_H zztwJhALwLE#1MuCc!d^dkoeT%D%~Xc1u^h7ci^SVln^p{*oP98L)o}4&#_cq7P;QL zJ1t?ir&12o;rfnT&*q!f*uw|1YQ?cs4pltoKby&_jl}}%K0MHXb_oHkIzB5OmX%i} zr9`2b@~8{B)C|RBXv?= ze1+ty_i2Z4OZ`KQ`{`Q4-)_H*?DbhY7)G;6*_wRE&DTW549*_7l#^nTUC%cw3lSdI z3!1K>n;-HX)LTz}tX$XZ{`uARaWIq5W|qQzwQ3N>r$Sio(*)n)tRm+tOp8D7DTLZR z6F+l#n$z07Sboy!H1=#go^vlgHbpbbJ7_f7cjMAYEh4jTm%1>>%=NfH5liM0qOqXd z5t+K5mo;$>CI+1RC#e1Jy)y}63G7zK-iYZ#<7}r+exNXxtazJd*s0P87k79wP^B-j zd+67u^h3mSVIy7TAzPw5VX57-zKWMz)P=b+Z6VbAPm8=JBB0{%yC&X&O(o3Hgr zARpmnHrKpQX9Pq9Lq;?ZSt(0)ZTlZj{l8o+^>&}#&6n6KlJV=&tq?u(tzR!1mat-Q zc0JYQjsf4r*v8wgHmhMd)eSh`of##LI7NY}if5671h54S0bkYh+*OW?7k_x;DoM3=w$$t-BTa?rQl;CZ zGNlaZW;5*6>m#Ow=5i(lCdOxaRl8q_;`GsCA{?Q{)&%tf_D!mmM4&6#00AbC2Mf6U zUgqY5{Aib1gElv19slbGm+e@Aqy9-Fc}6=8nY z4@n{l92g(}AVFlMbfMQg#@R)y-|=EClvN`j_V)?Rt0pN0wNV<(b0vZvLJx1$$fI=v z(S`dNMZh}y{+^mZmr_2SoV}5U@fxx(a@t<7La?(9!>CIL#2Vb~pam@T?KW)fv|h?Y zt!8MTiiQR%B3%X-R0JeR$Xv1Vh46051?dh(uUP&*v7lnN#$c9$@?GvP@43Td z+mFLPV5poc^v9QoNuDr~L@P+Mg*7XNWR2&Xg?1lr7%B>U|b$1`SQ|(3&?99 z3y{|&)s31nHJA=TaQkeK%wd!aZShbSBl{C%c7Nmrh?Ykm#2lo5FV%j)h{79EE#8h+ zJs`ua;DylFPz3h$=;F0=wD_*LE#E8^m!sH5*JK(Q7VoSg=%N!d@h``ZejRc>=13z5 z_xY04m$I`Ti#aLnn4T1zY@4_0JjUKC-4mVQ=(5`;+s$LvA+{!|J3LoQS(0&A4O6%$yyyI&$@dQ<`Dulr}JW`hv$lmp| zWGGaTiQr;~4>hv^B7RRHJ~$V?+6u%A9|I#J=UT11hf3}kR5akg@3jJJH2D%^X{3aR z8QW3IkU}en$%VWMSO3&3prE6;^p{E^-A^Nv-a8H|{*3TpW6_|(PrbtfjcY?=K)o_v z6e8R+4y0~CvOA&%g_vrn5g{3@78ClRByPBWLNZ65lg_lmHtft)uQo$q-<)O z^O8Y#1Qh!aJhMLF|dbINVb)?`B7wN@Gs{;WUeO2s`FS{X~PJ-4Tl5o}HedW#mTkn-MHM zCwn-*ZLW@uF(fIDaF+tB0EwijOPdxmV<7TMLaJ!7S+PESHGKH^Fc7U zpr`QO`Flif!0;e4zGjUXssuEF#D^x3-}XReaDh_T!^t-LI|g}NmPrEJ&z-fLo9Y%0!0I%^vZBgLh?es$fPqBo--m`dyi4Yxv2QGZg#MFm8SU4zo7 z6L^qj(m1DWRnwQQ-B_umUXEF>Z$A7_I`K~dP{J;qED0gRN&jX_wV%3p_JkezW zrQe$tLk^;&O&C!bHT1d{Lg$YuI@QZUYGt+9eAEx$R?F~CxK*lnNg2=3XKvSS+cn|xkm`UL z=Yi29sm8H-c|mMqI6xT0L2_{{jdbr+kZMLwS$4klmj2#XT*^PmHy2u9tkfnHsc9xr z_xh=AQ7}2jE}AxBm<$n5NGX4x`^JIBfU%c^16%73FwB~>6+!DIEZ7|Mix|iXek#L| zs~dP$=q6+IqR`DAZ7-aYn{mHU?`@VsjzyWkpybRE?$z+Id>ulPnyRcmdiW(G!EQJj z!X!K(>}=%eg5j3XfWOZ9RXhhDcJwkZrcJ62xV73A_J8y^dsba)@0ZygZ6@vyiHi^t ze@>Aww%t+LVa3^$ghz_KqbbW~w$KKg)46Rcwk9PMAcUr?>E_|7xZ{ezqqVSt}uq zY3voPA&t;LOntX_)}TzKZeiqzPwv*zOhKf05SLLo=H8SvfwU|&m=l`98}NQ$_WXg9 zkkP9_9Y-OOloIl|K&l2R6z&Lc}!r&;AAG%LI5CB zO_^y4X0Q^7RC+yTB=V*NDV+k{5*}4)Vq(igB%E|bPi2tJGWYj_B(quf_MN&%io1H} zlns)FZbl*@h)ovIBdv%^QrDy4fGq5gPo}cwu#DgqLGls#eB0Tnq4dU`A}MSxzsk1;n2u|7)j^>FMkcxnA4}()d0XmEOD8{)b)CM+v<5ivt)NH?Kr#p z!;yLn{FKdL=wg2EpY2=+79+;m2lOB6H|nNdYu`p$BoM`PX@I* zOG`Zsd6W8wt`rG5fgiPr(VOYQF-z=L8jFDHvUp~uw!w4+_k7zT2tWId=U*)H8Z^%Y zlon|buw1E=O1TPY`i;dOS0@+xnkpE$DY)l2Sd|l@T_eLoaQd6dZe)3Tr2VCkbq zN;VL1kk|w}C+r|*Fts)3tHs34$g^KZdeTbWry9rMP4b&9+_SMhJLco{)mn~06bt;I ziC@MvuI1kAv{rHLi2Ylm_mO!KqlCF6Ib^r=*Rn^)iFero#N6;Kt6 zwYgh)0MKsj#k)Syd^9TP$@-DWV|XjcQW7(MU^Le^OMofIHrY0@Qh#!4xzY=nn#QeC z9cQo5SIF`7R?XKZu?f-3bEE6CIAlx1zxYZ2Q#A4MN!&KM@?LzRSHmDDoFClxHP_s8 z!r|>=3i3=AUqma9pHJI{(QBHa36E~-=6l$S*S(k1u?NL{f#cZ*tRV{Oen@vKO-Y!R5acd z_p4!3@GA?dbi6YrCKZ%4`W;V&UU30jFmGM`2tJ8m^#1%)Q{<0f8|hE^L^MW;syMze zi8{sEQ+Q}xxw6e8=C#6!fBO16#`xsLLXHiUe;h@0?(m_vlb2VOWUR6&8tbgD@_$ZH zZm)=!R%u1Sy=i6JQYP9Zrf6Y7%NKk*BRo>pS4dy;kWkIzjFf*Q;^>B7)v~QhT?2*| zM@Ee{^JR#zS*tMvj2J#h{_RR*;&_O0D4ds;4cqa`#uWXu#&~98m64be2NYhd%N0sf zQK?VE@)C;GX^Z&Pi$hz&e+dQCMQ7PM6jEo@9dM@m*bP#pehoN% zCXjEvnD68=a!Iy3Z(XM;NI=FAcvZ9^7pY#D z`xu9c1UDxWpit0sob!WqUH!0QZ1Ppd&b`msU3spY-tHS$B?Hcv;`X;T8IsE8+HrVW zb3R@B^PZ0&)myhf+ikG?x$ofy3{^?Xw`RNvu&dC?m5Gk1lhv_g+f9 zjPM4@CiiE)ttE?n%Dem{<@*CdATf0Z+=W-=n8qfU@@%O2dWLxh4=vd_yKj4` zJ$+t4$Z&m77^ZLaLG4yso|^OP*zdy%ki@HHgncWqlns=YHw`|nYk@oSJPNC0JS2PG zZkD-eyj!_Vlma8n z#w0Ri?*~oCzdt|!dQl*={HNwSvLVOQS>n)va;xi1A?+|7menwqwtjoB{7(SUJOpah z!f1}xH@>}T23}S=4VG%!>@GACm=efn^P-H1su{HmkP98HQTlRK1xu8xq?Ks<{00Ma zd{QpJEF*9tn%Kjd&kK&8ai$fD_z#yuPCm()*w@~_W+KaZGxgb!He@{p{w|(eC@I%t zEAlFs>WSKJtz8=fg$MOcuhEygORPg==mG*hDi;Vx7XbUt{=c-qJ)$zhZL)o0O%-Eh{>>#*o*m@b|ftBZWZx=)_U z_p{%5v|-_|HuuFHGU??27N$=r;vEuY;qyfk3m>>DGRf=4GxRQFDWL@bdK|FSU=xCD znUDZw{)NwT2AoxuV~ag{;n&Wv6yjf7Y4|jh>(>)<@bUDHx)|W|JU@+pbU! z8j=!(a!IXnn0k|lV_Ef2P!QyF-gcZ8rLbxiXE}6g`{(*hWbz$OikvF_Q->2C*l`bQ zhW+Xd9(XOOD+y{v0D^HQU)F3<*Zf|4J-!m@qSBy4XNo08 z@uAcA(IsoAZj3{b7{R3O_13=k(GAdqD<(4Vpn0BHe~R6E{pzY?H&xeVck{3$PorRK zl(l+X0{>$Lr1atiYX#jt$f0+*{#LR2(yPNa6N_$cC-Za;#k&=2@t&3vz#m9}0G!W+ z0OyMh?t@)tWMxcegwI#}Y#MZWw%K(~?CL%X({S*y#>_W@180@va(7(UMbTGKzJs`ZHF zm(CX@4b;wylpljkIM4J|B{xRVIH z(-4Jwp~z_~tC6YX&{VbG&+dVpZqh_<^efvkby8Ys9>-iwrLNg>O zEN;pgnU#k4)oJ@>+>h|5!bJ++Hnz&hsoC)J!ERF|GmJrv)`llz}clu=1daxC}aM!H$SLLmD%qQvYs0mPV))>@U3x`;gvS(bV|Dq%|~`%tGwy_JP@V z8Py4!+ryP@euu6v+y@Yn4c!9A_6A5PM7 z6l?XHMSXw$Eu~(dMKce+E3*|L7jy)leC9!S=)4cR6Pa7{^`3k2eVoHt-r87X5U^kR z!U})d`Dp+1`zOtxw8j*M8b&nSq3Es8!* zk)XsdF4)C5D8`hanGTrFY`s1VAZBFRO_|^c7$|y(hRyHdR*3EQ>-3S_sy7IvBg%>GV%)_F1}U!q@d^Pn4fDVM@ukt?VXHo-_w%+ zui7gU7Y_ZA|0>G?@8e;XY)0vkT#(8WZ6L}wR%Od}E~mR;BeA7skC7za(V?83SN?}} zMTfH~_rZ$O&FQ6S?1oiDczjeDnF)Q#x)N)dl-|F&#MnlTV0UXszv?0lnEH+kq!k{U zeh;XOSI!cjmr2yra|*2ji$2fKS&gN#TgxU8J)mkQ)+`{o2yDaNxBqPM7%`qvh=D~c zl`R%r0cWb@5cc(`w$KvM$<(nBWUPI}y$Cs-1F^c9*7~IWdZLxlSLw(OsvHZRy2NeN zwBo7PXkeuZ8N{b4Yt8JlSzxA(0Q#iT&_3xxwpzxgSVvWNH?2IpI(Nf*G68lta zSPtqtk;49OPz^X5*#&(pllcd`yIzjFjtGY=#4j@%oVMlk)i%oGeVE{oCH8RynR>Jl zI%m4G$j&}>pD$<{eiU9IZujg7e5-+#Nv=ykEO0QU5!E8Pym$KcYyu>1Y!*(h?C#Ov zXAbjbPncK3KiQ^p=J-iG$N2~|bN4&%mR!AKwV>x4n{hz#H`STi)F?b>(zk z{yHt@^w~sf&FM*_T!tedqXN2L>>p$TgVUi@m0b6w8l&L7ZP!Vl5B6b-2O?OZ+r+_6 zIyESxZ!tTqJ@sbz1`$)tu|nl+SHWje7;=z4S(p}$z_;B~{N$y*b6(}p3SOD>(@vdM zmvF()Pm|KBmgb38EmE2y+XS%3VW^L}3V}jacPM4K9l3)vG6pF-)U*zA;Ct?wdQzC! zPbk8$V{_u-tOTMnCfGF?j++BSMT(rd-z?C@@6P&Mq%}ANo6dHURS)Xge3_$8`5e

Bi7O(sK{jpTjqdqI3wO8MRE8HE|FoDGv* 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 literal 0 HcmV?d00001 From 918c114965504cc47f8b1f5a34e572754f602374 Mon Sep 17 00:00:00 2001 From: Moilk Date: Wed, 10 Apr 2019 15:00:59 +0800 Subject: [PATCH 2/2] =?UTF-8?q?=E7=AC=AC=E4=BA=8C=E5=B0=8F=E8=8A=82?= =?UTF-8?q?=E5=AE=8C=E6=88=90=E8=8A=82=E5=A4=B4=E7=9A=84=E4=B8=80=E9=83=A8?= =?UTF-8?q?=E5=88=86?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- docs/book/19-Type-Information.md | 79 +++++++++++++++++++++++++++++++- 1 file changed, 77 insertions(+), 2 deletions(-) diff --git a/docs/book/19-Type-Information.md b/docs/book/19-Type-Information.md index e2e8f79..1369377 100644 --- a/docs/book/19-Type-Information.md +++ b/docs/book/19-Type-Information.md @@ -82,14 +82,89 @@ Triangle.draw() -## Class对象 +## `Class`对象 + +要理解 RTTI 在 Java 中的工作原理,首先必须知道类型信息在运行时是如何表示的。这项工作是由称为**`Class`对象**的特殊对象完成的,它包含了与类有关的信息。实际上,`Class`对象就是用来创建该类所有"常规"对象的。Java使用`Class`对象来实现RTTI,即便是类型转换这样的操作都是用`Class`对象实现的。不仅如此,`Class`类还提供了很多使用RTTI的其它方式。 + +类是程序的一部分,每个类都有一个`Class`对象。换言之,每当我们编写并且编译了一个新类,就会产生一个`Class`对象(更恰当的说,是被保存在一个同名的`.class`文件中)。为了生成这个类的对象,Java虚拟机(JVM)先会调用"类加载器"子系统把这个类加载到内存中。 + +类加载器子系统可能包含一条类加载器链,但有且只有一个**原生类加载器**,它是JVM实现的一部分。原生类加载器加载的是"可信类"(包括Java API类)。它们通常是从本地盘加载的。在这条链中,通常不需要添加额外的类加载器,但是如果你有特殊需求(例如以某种特殊的方式加载类,以支持Web服务器应用,或者通过网络下载类),也可以挂载额外的类加载器。 + +所有的类都是第一次使用时动态加载到JVM中的,当程序创建第一个对类的静态成员的引用时,就会加载这个类。 + +> 其实构造器也是类的静态方法,虽然构造器前面并没有`static`关键字。所以,使用`new`操作符创建类的新对象,这个操作也算作对类的静态成员引用。 + +因此,Java程序在它开始运行之前并没有被完全加载,很多部分是在需要时才会加载。这一点与许多传统编程语言不同,动态加载使得Java具有一些静态加载语言(如C++)很难或者根本不可能实现的特性。 + +类加载器首先会检查这个类的`Class`对象是否已经加载,如果尚未加载,默认的类加载器就会根据类名查找`.class`文件(如果有附加的类加载器,这时候可能就会在数据库中或者通过其它方式获得字节码)。这个类的字节码被加载后,JVM会对其进行验证,确保它没有损坏,并且不包含不良的Java代码(这是Java安全防范的一种措施)。 + +> 译者注:这里对类加载机制讲得不是很清楚,可以参考《深入理解Java虚拟机:JVM高级特性与最佳实践(第2版)》第7章 + +一旦某个类的`Class`对象被载入内存,它就可以用来创建这个类的所有对象。下面的示范程序可以证明这点: + +```java +// typeinfo/SweetShop.java +// Examination of the way the class loader works +class Cookie { + static { System.out.println("Loading Cookie"); } +} + +class Gum { + static { System.out.println("Loading Gum"); } +} + +class Candy { + static { System.out.println("Loading Candy"); } +} + +public class SweetShop { + public static void main(String[] args) { + System.out.println("inside main"); + new Candy(); + System.out.println("After creating Candy"); + try { + Class.forName("Gum"); + } catch(ClassNotFoundException e) { + System.out.println("Couldn't find Gum"); + } + System.out.println("After Class.forName(\"Gum\")"); + new Cookie(); + System.out.println("After creating Cookie"); + } +} +/* Output: +inside main +Loading Candy +After creating Candy +Loading Gum +After Class.forName("Gum") +Loading Cookie +After creating Cookie +*/ +``` + +上面的代码中,`Candy`、`Gum`和`Cookie`这几个类都有一个`static{...}`静态初始化块,这些静态初始化块在类第一次被加载的时候就会执行。也就是说,静态初始化块会打印出相应的信息,告诉我们这些类分别是什么时候被加载了。而在`main()`里边,创建对象 的代码都放在了`print()`语句之间,以帮助我们判断类加载的时间点。 + +从输出中可以看到,`Class`对象仅在需要的时候才会被加载,`static`初始化是在类加载时进行的。 + +代码里面还有特别有趣的一行: + +```java +Class.forName("Gum"); +``` + +所有`Class`对象都属于`Class`类,而且它跟其他普通对象一样,我们可以获取和操控它的引用(这也是类加载器的工作)。`forName()`是`Class`类的一个静态方法,我们可以使用`forName()`根据目标类的类名(`String`)得到该类的`Class`对象。上面的代码忽略了`forName()`的返回值,因为那个调用是为了得到它产生的"副作用"。从结果可以看出,`forName()`执行的副作用是如果`Gum`类没有被加载就加载它,而在加载的过程中,`Gum`的`static`初始化块被执行了。 + +还需要注意的是,如果`Class.forName()`找不到要加载的类,它就会抛出异常`ClassNotFoundException`。上面的例子中我们只是简单地报告了问题,但在更严密的程序里,就要在异常处理程序中解决这个问题。 + + ## 类型转换检测 - + ## 注册工厂