📄 chap08.html
字号:
<PRE>
<FONT FACE="Courier New">begin</FONT></P>
<FONT SIZE="2"><P></FONT><FONT FACE="Courier New">// On CD-ROM in file linking/ex1/Example1.java
<P>class Example1 {</P>
<P> </P>
<P> // Assume this application is invoked with one command-line</P>
<P> // argument, the string "Hi!".</P>
<P> public static void main(String[] args) {</P>
<P> </P>
<P> // argZero, because it is assigned a String from the command</P>
<P> // line, does not reference a string literal. This string</P>
<P> // is not interned.</P>
<P> String argZero = args[0];</P>
<P> </P>
<P> // literalString, however, does reference a string literal.</P>
<P> // It will be assigned a reference to a String with the value</P>
<P> // "Hi!" by an instruction that references a</P>
<P> // CONSTANT_String_info entry in the constant pool. The</P>
<P> // "Hi!" string will be interned by this process.</P>
<P> String literalString = "Hi!";</P>
<P> </P>
<P> // At this point, there are two String objects on the heap</P>
<P> // that have the value "Hi!". The one from arg[0], which</P>
<P> // isn't interned, and the one from the literal, which</P>
<P> // is interned.</P>
<P> System.out.print("Before interning argZero: ");</P>
<P> if (argZero == literalString) {</P>
<P> System.out.println("they're the same string object!");</P>
<P> }</P>
<P> else {</P>
<P> System.out.println("they're different string objects.");</P>
<P> }</P>
<P> </P>
<P> // argZero.intern() returns the reference to the literal</P>
<P> // string "Hi!" that is already interned. Now both argZero</P>
<P> // and literalString have the same value. The non-interned</P>
<P> // version of "Hi!" is now available for garbage collection.</P>
<P> argZero = argZero.intern();</P>
<P> System.out.print("After interning argZero: ");</P>
<P> if (argZero == literalString) {</P>
<P> System.out.println("they're the same string object!");</P>
<P> }</P>
<P> else {</P>
<P> System.out.println("they're different string objects.");</P>
<P> }</P>
<P> }</P>
<P>}</P>
</FONT><FONT SIZE="2"><P> </P></FONT><FONT FACE="Courier New">end</FONT></P></PRE>
</PRE>
<P>When executed with the string <FONT FACE="Courier New">"Hi!"</FONT> as the first command-line argument, the <FONT FACE="Courier New">Example1</FONT> application prints the following:</P>
<PRE><P><FONT FACE="Courier New">begin</FONT></P>
<FONT FACE="Courier New"><P>Before interning argZero: they're different string objects.</P>
<P>After interning argZero: they're the same string object!</P>
</FONT><P><FONT FACE="Courier New">end</FONT></P></PRE>
<H3><P>Resolution of Other Types of Entries</P>
</H3><P>The CONSTANT_Integer_info, <FONT FACE="Courier New">CONSTANT_Long_info</FONT>, <FONT FACE="Courier New">CONSTANT_Float_info</FONT>, <FONT FACE="Courier New">CONSTANT_Double_info</FONT> entries contain the constant values they represent within the entry itself. These are straightforward to resolve. To resolve this kind of entry, many virtual machine implementations may not have to do anything but use the value as is. Other implementations, however, may choose to do some processing on it. For example, a virtual machine on a little-endian machine could choose to swap the byte order of the value at resolve time.</P>
<P>Entries of type <FONT FACE="Courier New">CONSTANT_Utf8_info</FONT> and <FONT FACE="Courier New">CONSTANT_NameAndType_info</FONT> are never referred to directly by instructions. They are only referred to via other types of entries, and resolved when those referring entries are resolved.</P>
<H3><EM><P>Compile-Time Resolution of Constants</P>
</EM></H3><P>As mentioned in Chapter 7, "The Lifetime of a Class," references to static final variables initialized to a compile-time constant are resolved at compile-time to a local copy of the constant value. This is true for constants of all the primitive types and of type <FONT FACE="Courier New">java.lang.String</FONT>.</P>
<P>This special treatment of constants facilitates two features of the Java language. First, local copies of constant values enable static final variables to be used as <FONT FACE="Courier New">case</FONT> expressions in <FONT FACE="Courier New">switch</FONT> statements. The two virtual machine instructions that implement <FONT FACE="Courier New">switch</FONT> statements in bytecodes, <FONT FACE="Courier New">tableswitch</FONT> and <FONT FACE="Courier New">lookupswitch</FONT>, require the <FONT FACE="Courier New">case</FONT> values in-line in the bytecode stream. These instructions do not support run-time resolution of <FONT FACE="Courier New">case</FONT> values. See Chapter 16, "Control Flow," for more information about these instructions.</P>
<P>The other motivation behind the special treatment of constants is conditional compilation. Java supports conditional compilation via <FONT FACE="Courier New">if</FONT> statements whose expressions resolve to a compile-time constant. Here韘 an example:</P>
<PRE><P><FONT FACE="Courier New">begin</FONT></P>
<FONT SIZE="2"><P></FONT><FONT FACE="Courier New">// On CD-ROM in file linking/ex2/AntHill.java
<P>class AntHill {</P>
<P> </P>
<P> static final boolean debug = true;</P>
<P>}</P>
</FONT><FONT SIZE="2"><P> </P></P>
<P></FONT><FONT FACE="Courier New">// On CD-ROM in file linking/ex2/Example2.java
<P>class Example2 {</P>
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -