我们都知道JAVA是一种解析型说话,这就抉择JAVA文件编译后不是机械码,而是一个字节码文件,也就是CLASS文件。而这样的文件是存在纪律的,经由反编译工具是可以还原回来的。例如Decafe、FrontEnd,YingJAD和Jode等等软件。下面是《Nokia中Short数组转换算法》 类中Main函数的ByteCode:& g7 q! @6 H" O! t4 Q
0 ldc #16
* `1 z% x5 {- {6 h 2 invokestatic #185 Q) p4 H9 S6 c" @ c
5 astore_1
7 @4 y' m, _4 U8 R 6 return
8 w# u6 ^5 x. U 其源代码是:short [] pixels = parseImage("/ef1s.png");' g5 f* e/ x# V7 A3 @
我们经由过程反编译工具是可以还原出以上源代码的。而经由过程简单的剖析,我们也能自己写出源代码的。& ^' H9 l, e5 r2 ~* G9 K
第一行:ldc #16
7 ~6 R4 |3 b7 M ldc为虚拟机的指令,浸染是:压入常量池的项,形式如下$ ]9 K# ?% |, o
ldc index# I) Z. N3 C- j Z
这个index就是膳缦沔的16,也就是在常量池中的有用索引,当我们去看常量池的时辰,我们就会找到index为16的值为String_info,琅缦沔存了/ef1s.png.
6 q! _- Y/ ?! a9 P. l& E 所以这行的意思就是把/ef1s.pn作为一个String存在常量池中,其有用索引为16。
: d0 g/ i8 X- }+ ?8 C) l 第二行:2 invokestatic #18
8 Z) y" Q7 \+ k8 O4 w- G invokestatic为虚拟机指令,浸染是:挪用类(static)体例,形式如下& s. Y- }& X w& y
invokestatic indexbyte1 indexbyte2( U* B# B2 x; ]. `/ [+ U) ^
其中indexbyte1和indexbyte2必需是在常量池中的有用索引,而是指向的类型必需有Methodref标识表记标帜,对类名,体例名和体例的描述符的引用。
& s. [, Z1 {8 ?; G 所以当我们看常量池中索引为18的处所,我们就会获得以下信息:( I' H: g+ e: Z0 a+ Q5 q
Class Name : cp_info#1
' G( Z% J+ n3 o( d- D8 G0 i0 u Name Type : cp_info#19
# O+ H! O' K. I0 a; e% a: i 1 和19都是常量池中的有用索引,值就是右边中的值,再往下跟踪我就不多说了,有乐趣的伴侣可以去JAVA虚拟机规范。
$ Q+ X! b$ D0 U8 o, N 这里我简单介绍一下parseImage(Ljava/lang/String;)[S 的意思。
: Z0 c5 q' v& @# u6 e" _4 N5 g/ W 这就是parseImage这个函数的运行,我们反过来看看parseImage的原型就年夜白了6 w& `, Y: E- A" W/ u9 F; U
short [] parseImage(String)
4 m J- m+ A' }, Y1 P* a 那么Ljava/lang/String;就是说需要传入一个String对象,而为什么前面要有一个L呢,这是JAVA虚拟机用来暗示这是一个Object。如不美观是根基类型,这里就不需要有L了。然后返回为short的一维数组,也就是对应的[S。是不是很有意思,S对应着Short类型,而 “[”对应一维数组,那有些伴侣要问了,两维呢,那就“[[”,呵呵,是不是很有意思。
, y- X0 ^6 g( A' n- r 好了,挪用了函数,返回的值要保留下来吧。那么就是第三行要做的工作了。. r5 a r, _5 q
第三行:5 astore_1% a5 E" v$ O6 I1 q3 w5 @$ [% _2 R6 k
呵呵,很简单的。可是饶暌剐文章,也是斗劲轻易杂乱的处所。1 N; A) {/ M5 r3 H5 @. s, t
astore_为虚拟机指令,浸染为:将当前reference存储到局部变量中去。而必需是对当前框架的局部变量的有用索引。打个例如,可能我们这个函数中可能还要用到这个局部变量,我们可以经由过程来找到它。例如挪用虚拟机指令:
5 I' D8 R/ Y" w/ u o4 s aload_1,就能获得该值。) U4 D- X/ S3 ` _
第四行:6 return+ K/ b" D9 _8 x, a" C0 V8 Z# T' }$ o
同样的,return也是虚拟机指令了,它的浸染为:细腻式返回void。
8 U; Z3 T1 W- x 这里也就是退出main函数。
+ W9 m# ]# l4 ]. T3 J" ^8 T- F* e+ T
---------------------------------------------------------------------------- |