UNPKG

epubjs

Version:

Render ePub documents in the browser, across many devices

371 lines (358 loc) 60 kB
<?xml version="1.0" encoding="UTF-8" standalone="no"?> <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.1//EN" "http://www.w3.org/TR/xhtml11/DTD/xhtml11.dtd"> <html xmlns="http://www.w3.org/1999/xhtml"><head><title>Methods</title><link rel="stylesheet" href="core.css" type="text/css"/><meta name="generator" content="DocBook XSL Stylesheets V1.74.0"/></head><body><div class="sect1" title="Methods"><div class="titlepage"><div><div><h1 class="title"><a id="learnjava3-CHP-5-SECT-2"/>Methods</h1></div></div></div><p>Methods appear inside class bodies. They contain local variable declarations and other Java statements that are executed when the method is invoked. Methods may return a value to the caller. They always specify a return type, which can be a primitive type, a reference type, or the type <a id="I_indexterm5_id689583" class="indexterm"/><code class="literal">void</code> , which indicates no returned value. Methods may take arguments, which are values supplied by the caller of the method.</p><p>Here’s a simple example:</p><a id="I_5_tt241"/><pre class="programlisting"> <code class="kd">class</code> <code class="nc">Bird</code> <code class="o">{</code> <code class="kt">int</code> <code class="n">xPos</code><code class="o">,</code> <code class="n">yPos</code><code class="o">;</code> <code class="kt">double</code> <code class="nf">fly</code> <code class="o">(</code> <code class="kt">int</code> <code class="n">x</code><code class="o">,</code> <code class="kt">int</code> <code class="n">y</code> <code class="o">)</code> <code class="o">{</code> <code class="kt">double</code> <code class="n">distance</code> <code class="o">=</code> <code class="n">Math</code><code class="o">.</code><code class="na">sqrt</code><code class="o">(</code> <code class="n">x</code><code class="o">*</code><code class="n">x</code> <code class="o">+</code> <code class="n">y</code><code class="o">*</code><code class="n">y</code> <code class="o">);</code> <code class="n">flap</code><code class="o">(</code> <code class="n">distance</code> <code class="o">);</code> <code class="n">xPos</code> <code class="o">=</code> <code class="n">x</code><code class="o">;</code> <code class="n">yPos</code> <code class="o">=</code> <code class="n">y</code><code class="o">;</code> <code class="k">return</code> <code class="n">distance</code><code class="o">;</code> <code class="o">}</code> <code class="o">...</code> <code class="o">}</code></pre><p>In this example, the class <code class="literal">Bird</code> defines a method, <code class="literal">fly()</code>, that takes as arguments two integers: <code class="literal">x</code> and <code class="literal">y</code>. It returns a <code class="literal">double</code> type value as a result, using the <a id="I_indexterm5_id689637" class="indexterm"/><code class="literal">return</code> keyword.</p><p>Our method has a fixed number of arguments (two); however, methods can have <span class="emphasis"><em>variable-length argument lists</em></span>, which allow the method to specify that it can take any number of arguments and sort them itself at runtime. We provide more details later in this chapter.</p><div class="sect2" title="Local Variables"><div class="titlepage"><div><div><h2 class="title"><a id="learnjava3-CHP-5-SECT-2.1"/>Local Variables</h2></div></div></div><p><a id="I_indexterm5_id689663" class="indexterm"/> <a id="I_indexterm5_id689669" class="indexterm"/> <a id="idx10248" class="indexterm"/>Our <code class="literal">fly()</code> method declares a local variable called <code class="literal">distance</code>, which it uses to compute the distance flown. A local variable is temporary; it exists only within the scope (the block) of its method. Local variables are allocated when a method is invoked; they are normally destroyed when the method returns. They can’t be referenced from outside the method itself. If the method is executing concurrently in different threads, each thread has its own version of the method’s local variables. A method’s arguments also serve as local variables within the scope of the method; the only difference is that they are initialized by being passed in from the caller of the method.</p><p>An object created within a method and assigned to a local variable may or may not persist after the method has returned. As with all objects in Java, it depends on whether any references to the object remain. If an object is created, assigned to a local variable, and never used anywhere else, that object is no longer referenced when the local variable disappears from scope, so garbage collection removes the object. If, however, we assign the object to an instance variable of an object, pass it as an argument to another method, or pass it back as a return value, it may be saved by another variable holding its reference. We’ll discuss object creation and garbage collection in more detail shortly.<a id="I_indexterm5_id689728" class="indexterm"/></p></div><div class="sect2" title="Shadowing"><div class="titlepage"><div><div><h2 class="title"><a id="learnjava3-CHP-5-SECT-2.2"/>Shadowing</h2></div></div></div><p><a id="idx10233" class="indexterm"/> <a id="idx10250" class="indexterm"/> <a id="idx10258" class="indexterm"/>If a local variable and an instance variable have the same name, the local variable <span class="emphasis"><em>shadows</em></span> or hides the name of the instance variable within the scope of the method. In the following example, the local variables <code class="literal">xPos</code> and <code class="literal">yPos</code> hide the instance variables of the same name:</p><a id="I_5_tt242"/><pre class="programlisting"> <code class="kd">class</code> <code class="nc">Bird</code> <code class="o">{</code> <code class="kt">int</code> <code class="n">xPos</code><code class="o">,</code> <code class="n">yPos</code><code class="o">;</code> <code class="kt">int</code> <code class="n">xNest</code><code class="o">,</code> <code class="n">yNest</code><code class="o">;</code> <code class="o">...</code> <code class="kt">double</code> <code class="nf">flyToNest</code><code class="o">()</code> <code class="o">{</code> <code class="kt">int</code> <code class="n">xPos</code> <code class="o">=</code> <code class="n">xNest</code><code class="o">;</code> <code class="kt">int</code> <code class="n">yPos</code> <code class="o">=</code> <code class="nl">yNest:</code> <code class="k">return</code> <code class="o">(</code> <code class="n">fly</code><code class="o">(</code> <code class="n">xPos</code><code class="o">,</code> <code class="n">yPos</code> <code class="o">)</code> <code class="o">);</code> <code class="o">}</code> <code class="o">...</code> <code class="o">}</code></pre><p>When we set the values of the local variables in <code class="literal">flyToNest()</code>, it has no effect on the values of the instance variables.</p><div class="sect3" title="The “this” reference"><div class="titlepage"><div><div><h3 class="title"><a id="learnjava3-CHP-5-SECT-2.2.1"/>The “this” reference</h3></div></div></div><p>You can use the special reference <code class="literal">this</code> any time you need to refer explicitly to the current object or a member of the current object. Often you don’t need to use <code class="literal">this</code>, because the reference to the current object is implicit; such is the case when using unambiguously named instance variables inside a class. But we can use <code class="literal">this</code> to refer explicitly to instance variables in our object, even if they are shadowed. The following example shows how we can use <code class="literal">this</code> to allow argument names that shadow instance variable names. This is a fairly common technique because it saves having to make up alternative names. Here’s how we could implement our <code class="literal">fly()</code> method with shadowed variables:</p><a id="I_5_tt243"/><pre class="programlisting"> <code class="kd">class</code> <code class="nc">Bird</code> <code class="o">{</code> <code class="kt">int</code> <code class="n">xPos</code><code class="o">,</code> <code class="n">yPos</code><code class="o">;</code> <code class="kt">double</code> <code class="nf">fly</code> <code class="o">(</code> <code class="kt">int</code> <code class="n">xPos</code><code class="o">,</code> <code class="kt">int</code> <code class="n">yPos</code> <code class="o">)</code> <code class="o">{</code> <code class="kt">double</code> <code class="n">distance</code> <code class="o">=</code> <code class="n">Math</code><code class="o">.</code><code class="na">sqrt</code><code class="o">(</code> <code class="n">xPos</code><code class="o">*</code><code class="n">xPos</code> <code class="o">+</code> <code class="n">yPos</code><code class="o">*</code><code class="n">yPos</code> <code class="o">);</code> <code class="n">flap</code><code class="o">(</code> <code class="n">distance</code> <code class="o">);</code> <code class="k">this</code><code class="o">.</code><code class="na">xPos</code> <code class="o">=</code> <code class="n">xPos</code><code class="o">;</code> <code class="c1">// instance var = local vra</code> <code class="k">this</code><code class="o">.</code><code class="na">yPos</code> <code class="o">=</code> <code class="n">yPos</code><code class="o">;</code> <code class="k">return</code> <code class="n">distance</code><code class="o">;</code> <code class="o">}</code> <code class="o">...</code> <code class="o">}</code></pre><p>In this example, the expression <code class="literal">this.xPos</code> refers to the instance variable <code class="literal">xPos</code> and assigns it the value of the local variable <code class="literal">xPos</code>, which would otherwise hide its name. The only reason we need to use <code class="literal">this</code> in the previous example is because we’ve used argument names that hide our instance variables, and we want to refer to the instance variables. You can also use the <code class="literal">this</code> reference any time you want to pass a reference to “the current” enclosing object to some other method; we’ll show examples of that later.<a id="I_indexterm5_id689906" class="indexterm"/><a id="I_indexterm5_id689913" class="indexterm"/><a id="I_indexterm5_id689920" class="indexterm"/></p></div></div><div class="sect2" title="Static Methods"><div class="titlepage"><div><div><h2 class="title"><a id="learnjava3-CHP-5-SECT-2.3"/>Static Methods</h2></div></div></div><p><a id="idx10234" class="indexterm"/> <a id="idx10251" class="indexterm"/> <a id="idx10261" class="indexterm"/>Static methods (class methods), like static variables, belong to the class and not to individual instances of the class. What does this mean? Well, foremost, a static method lives outside of any particular class instance. It can be invoked by name, through the class name, without any objects around. Because it is not bound to a particular object instance, a static method can directly access only other static members (static variables and other static methods) of the class. It can’t directly see any instance variables or call any instance methods, because to do so we’d have to ask, “on which instance?” Static methods can be called from instances, syntactically just like instance methods, but the important thing is that they can also be used independently.</p><p>Our <code class="literal">fly()</code> method uses a static method: <a id="I_indexterm5_id689992" class="indexterm"/><code class="literal">Math.sqrt()</code>, which is defined by the <code class="literal">java.lang.Math</code> class; we’ll explore this class in detail in <a class="xref" href="ch11.html" title="Chapter 11. Core Utilities">Chapter 11</a>. For now, the important thing to note is that <a id="I_indexterm5_id690014" class="indexterm"/><code class="literal">Math</code> is the name of a class and not an instance of a <code class="literal">Math</code> object. (It so happens that you can’t even make an instance of the <code class="literal">Math</code> class.) Because static methods can be invoked wherever the class name is available, class methods are closer to C-style functions. Static methods are particularly useful for utility methods that perform work that is useful either independently of instances or in working on instances. For example, in our <code class="literal">Bird</code> class, we could enumerate all of the available types of birds that can be created:</p><a id="I_5_tt244"/><pre class="programlisting"> <code class="kd">class</code> <code class="nc">Bird</code> <code class="o">{</code> <code class="o">...</code> <code class="kd">static</code> <code class="n">String</code> <code class="o">[]</code> <code class="n">getBirdTypes</code><code class="o">()</code> <code class="o">{</code> <code class="o">...</code> <code class="o">}</code> <code class="o">}</code></pre><p>Here, we’ve defined a static method, <code class="literal">getBirdTypes()</code>, that returns an array of strings containing bird names. We can use <code class="literal">getBirdTypes()</code> from within an instance of <code class="literal">Bird</code>, just like an instance method. However, we can also call it from other classes, using the <code class="literal">Bird</code> class name:</p><a id="I_5_tt245"/><pre class="programlisting"> <code class="n">String</code> <code class="o">[]</code> <code class="n">names</code> <code class="o">=</code> <code class="n">Bird</code><code class="o">.</code><code class="na">getBirdTypes</code><code class="o">();</code></pre><p>Perhaps a special version of the <code class="literal">Bird</code> class constructor accepts the name of a bird type. We could use this list to decide what kind of bird to create.</p><p>Static methods also play an important role in various design patterns, where you limit the use of the <code class="literal">new</code> operator for a class to one method—a static method called a <span class="emphasis"><em>factory method</em></span>. We’ll talk more about object construction later, but suffice it to say that it’s common to see usage like this:<a id="I_indexterm5_id690114" class="indexterm"/><a id="I_indexterm5_id690121" class="indexterm"/><a id="I_indexterm5_id690128" class="indexterm"/></p><a id="I_5_tt246"/><pre class="programlisting"> <code class="n">Bird</code> <code class="n">bird</code> <code class="o">=</code> <code class="n">Bird</code><code class="o">.</code><code class="na">createBird</code><code class="o">(</code> <code class="s">"pigeon"</code> <code class="o">);</code></pre></div><div class="sect2" title="Initializing Local Variables"><div class="titlepage"><div><div><h2 class="title"><a id="learnjava3-CHP-5-SECT-2.4"/>Initializing Local Variables</h2></div></div></div><p><a id="idx10231" class="indexterm"/> <a id="idx10247" class="indexterm"/>In the <code class="literal">flyToNest()</code> example, we made a point of initializing the local variables <code class="literal">xPos</code> and <code class="literal">yPos</code>. Unlike instance variables, local variables must be initialized before they can be used. It’s a compile-time error to try to access a local variable without first assigning it a value:</p><a id="I_5_tt247"/><pre class="programlisting"> <code class="kt">void</code> <code class="nf">myMethod</code><code class="o">()</code> <code class="o">{</code> <code class="kt">int</code> <code class="n">foo</code> <code class="o">=</code> <code class="mi">42</code><code class="o">;</code> <code class="kt">int</code> <code class="n">bar</code><code class="o">;</code> <code class="n">bar</code> <code class="o">+=</code> <code class="mi">1</code><code class="o">;</code> <code class="c1">// compile-time error, bar uninitialized</code> <code class="n">bar</code> <code class="o">=</code> <code class="mi">99</code><code class="o">;</code> <code class="n">bar</code> <code class="o">+=</code> <code class="mi">1</code><code class="o">;</code> <code class="c1">// would be OK here</code> <code class="o">}</code></pre><p>Notice that this doesn’t imply local variables have to be initialized when declared, just that the first time they are referenced must be in an assignment. More subtle possibilities arise when making assignments inside conditionals:</p><a id="I_5_tt248"/><pre class="programlisting"> <code class="kt">void</code> <code class="n">myMethod</code> <code class="o">{</code> <code class="kt">int</code> <code class="n">foo</code><code class="o">;</code> <code class="k">if</code> <code class="o">(</code> <code class="n">someCondition</code> <code class="o">)</code> <code class="o">{</code> <code class="n">foo</code> <code class="o">=</code> <code class="mi">42</code><code class="o">;</code> <code class="o">...</code> <code class="o">}</code> <code class="n">foo</code> <code class="o">+=</code> <code class="mi">1</code><code class="o">;</code> <code class="c1">// Compile-time error, foo may not be initialized</code> <code class="o">}</code></pre><p>In this example, <code class="literal">foo</code> is initialized only if <code class="literal">someCondition</code> is <code class="literal">true</code>. The compiler doesn’t let you make this wager, so it flags the use of <code class="literal">foo</code> as an error. We could correct this situation in several ways. We could initialize the variable to a default value in advance or move the usage inside the conditional. We could also make sure the path of execution doesn’t reach the uninitialized variable through some other means, depending on what makes sense for our particular application. For example, we could simply make sure that we assign <code class="literal">foo</code> a value in both the <code class="literal">if</code> and <code class="literal">else</code> branch. Or we could return from the method abruptly:</p><a id="I_5_tt249"/><pre class="programlisting"> <code class="kt">int</code> <code class="n">foo</code><code class="o">;</code> <code class="o">...</code> <code class="k">if</code> <code class="o">(</code> <code class="n">someCondition</code> <code class="o">)</code> <code class="o">{</code> <code class="n">foo</code> <code class="o">=</code> <code class="mi">42</code><code class="o">;</code> <code class="o">...</code> <code class="o">}</code> <code class="k">else</code> <code class="k">return</code><code class="o">;</code> <code class="n">foo</code> <code class="o">+=</code> <code class="mi">1</code><code class="o">;</code></pre><p>In this case, there’s no chance of reaching <code class="literal">foo</code> in an uninitialized state, so the compiler allows the use of <code class="literal">foo</code> after the conditional.</p><p>Why is Java so picky about local variables? One of the most common (and insidious) sources of errors in C or C++ is forgetting to initialize local variables, so Java tries to help out. If it didn’t, Java would suffer the same potential irregularities as C or C++.<sup>[<a id="learnjava3-CHP-5-FNOTE-2" href="#ftn.learnjava3-CHP-5-FNOTE-2" class="footnote">13</a>]</sup><a id="I_indexterm5_id690327" class="indexterm"/><a id="I_indexterm5_id690334" class="indexterm"/></p></div><div class="sect2" title="Argument Passing and References"><div class="titlepage"><div><div><h2 class="title"><a id="learnjava3-CHP-5-SECT-2.5"/>Argument Passing and References</h2></div></div></div><p><a id="idx10219" class="indexterm"/> <a id="idx10229" class="indexterm"/> <a id="idx10245" class="indexterm"/>In the beginning of <a class="xref" href="ch04.html" title="Chapter 4. The Java Language">Chapter 4</a>, we described the distinction between primitive types, which are passed by value (by copying), and objects, which are passed by reference. Now that we’ve got a better handle on methods in Java, let’s walk through an example:</p><a id="I_5_tt250"/><pre class="programlisting"> <code class="kt">void</code> <code class="nf">myMethod</code><code class="o">(</code> <code class="kt">int</code> <code class="n">j</code><code class="o">,</code> <code class="n">SomeKindOfObject</code> <code class="n">o</code> <code class="o">)</code> <code class="o">{</code> <code class="o">...</code> <code class="o">}</code> <code class="c1">// use the method</code> <code class="kt">int</code> <code class="n">i</code> <code class="o">=</code> <code class="mi">0</code><code class="o">;</code> <code class="n">SomeKindOfObject</code> <code class="n">obj</code> <code class="o">=</code> <code class="k">new</code> <code class="n">SomeKindOfObject</code><code class="o">();</code> <code class="n">myMethod</code><code class="o">(</code> <code class="n">i</code><code class="o">,</code> <code class="n">obj</code> <code class="o">);</code></pre><p>The chunk of code calls <code class="literal">myMethod()</code>, passing it two arguments. The first argument, <code class="literal">i</code>, is passed by value; when the method is called, the value of <code class="literal">i</code> is copied into the method’s parameter (a local variable to it) named <code class="literal">j</code>. If <code class="literal">myMethod()</code> changes the value of <code class="literal">j</code>, it’s changing only its copy of the local variable.</p><p>In the same way, a copy of the reference to <code class="literal">obj</code> is placed into the reference variable <code class="literal">o</code> of <code class="literal">myMethod()</code>. Both references refer to the same object, so any changes made through either reference affect the actual (single) object instance. If we change the value of, say, <code class="literal">o.size</code>, the change is visible both as <code class="literal">o.size</code> (inside <code class="literal">myMethod()</code>) or as <code class="literal">obj.size</code> (in the calling method). However, if <code class="literal">myMethod()</code> changes the reference <code class="literal">o</code> itself—to point to another object—it’s affecting only its local variable reference. It doesn’t affect the caller’s variable <code class="literal">obj</code>, which still refers to the original object. In this sense, passing the reference is like passing a pointer in C and unlike passing by reference in C++.</p><p>What if <code class="literal">myMethod()</code> needs to modify the calling method’s notion of the <code class="literal">obj</code> reference as well (i.e., make <code class="literal">obj</code> point to a different object)? The easy way to do that is to wrap <code class="literal">obj</code> inside some kind of object. For example, we could wrap the object up as the lone element in an array:</p><a id="I_5_tt251"/><pre class="programlisting"> <code class="n">SomeKindOfObject</code> <code class="o">[]</code> <code class="n">wrapper</code> <code class="o">=</code> <code class="k">new</code> <code class="n">SomeKindOfObject</code> <code class="o">[]</code> <code class="o">{</code> <code class="n">obj</code> <code class="o">};</code></pre><p>All parties could then refer to the object as <code class="literal">wrapper[0]</code> and would have the ability to change the reference. This is not aesthetically pleasing, but it does illustrate that what is needed is the level of indirection.</p><p>Another possibility is to use <code class="literal">this</code> to pass a reference to the calling object. In that case, the calling object serves as the wrapper for the reference. Let’s look at a piece of code that could be from an implementation of a linked list:</p><a id="I_5_tt252"/><pre class="programlisting"> <code class="kd">class</code> <code class="nc">Element</code> <code class="o">{</code> <code class="kd">public</code> <code class="n">Element</code> <code class="n">nextElement</code><code class="o">;</code> <code class="kt">void</code> <code class="nf">addToList</code><code class="o">(</code> <code class="n">List</code> <code class="n">list</code> <code class="o">)</code> <code class="o">{</code> <code class="n">list</code><code class="o">.</code><code class="na">addToList</code><code class="o">(</code> <code class="k">this</code> <code class="o">);</code> <code class="o">}</code> <code class="o">}</code> <code class="kd">class</code> <code class="nc">List</code> <code class="o">{</code> <code class="kt">void</code> <code class="nf">addToList</code><code class="o">(</code> <code class="n">Element</code> <code class="n">element</code> <code class="o">)</code> <code class="o">{</code> <code class="o">...</code> <code class="n">element</code><code class="o">.</code><code class="na">nextElement</code> <code class="o">=</code> <code class="n">getNextElement</code><code class="o">();</code> <code class="o">}</code> <code class="o">}</code></pre><p>Every element in a linked list contains a pointer to the next element in the list. In this code, the <code class="literal">Element</code> class represents one element; it includes a method for adding itself to the list. The <code class="literal">List</code> class itself contains a method for adding an arbitrary <code class="literal">Element</code> to the list. The method <code class="literal">addToList()</code> calls <code class="literal">addToList()</code> with the argument <code class="literal">this</code> (which is, of course, an <code class="literal">Element</code>). <code class="literal">addToList()</code> can use the <code class="literal">this</code> reference to modify the <code class="literal">Element</code>’s <code class="literal">nextElement</code> instance variable. The same technique can be used in conjunction with interfaces to implement callbacks for arbitrary method invocations.<a id="I_indexterm5_id690638" class="indexterm"/><a id="I_indexterm5_id690645" class="indexterm"/><a id="I_indexterm5_id690652" class="indexterm"/></p></div><div class="sect2" title="Wrappers for Primitive Types"><div class="titlepage"><div><div><h2 class="title"><a id="learnjava3-CHP-5-SECT-2.6"/>Wrappers for Primitive Types</h2></div></div></div><p><a id="idx10236" class="indexterm"/> <a id="idx10253" class="indexterm"/> <a id="idx10257" class="indexterm"/> <a id="idx10264" class="indexterm"/>As we described in <a class="xref" href="ch04.html" title="Chapter 4. The Java Language">Chapter 4</a>, there is a schism in the Java world between class types (i.e., objects) and primitive types (i.e., numbers, characters, and Boolean values). Java accepts this tradeoff simply for efficiency reasons. When you’re crunching numbers, you want your computations to be lightweight; having to use objects for primitive types complicates performance optimizations. For the times you want to treat values as objects, Java supplies a standard wrapper class for each of the primitive types, as shown in <a class="xref" href="ch05s02.html#learnjava3-CHP-5-TABLE-1" title="Table 5-1. Primitive type wrappers">Table 5-1</a>.</p><div class="table"><a id="learnjava3-CHP-5-TABLE-1"/><p class="title">Table 5-1. Primitive type wrappers</p><div class="table-contents"><table summary="Primitive type wrappers" style="border-collapse: collapse;border-top: 0.5pt solid ; border-bottom: 0.5pt solid ; "><colgroup><col/><col/></colgroup><thead><tr><th style="text-align: left"><p>Primitive</p></th><th style="text-align: left"><p>Wrapper</p></th></tr></thead><tbody><tr><td style="text-align: left"><p> <a id="I_indexterm5_id690780" class="indexterm"/> <code class="literal">void</code> </p></td><td style="text-align: left"><p> <a id="I_indexterm5_id690797" class="indexterm"/> <code class="literal">java.lang.Void</code> </p></td></tr><tr><td style="text-align: left"><p> <a id="I_indexterm5_id690814" class="indexterm"/> <code class="literal">boolean</code> </p></td><td style="text-align: left"><p> <a id="I_indexterm5_id690831" class="indexterm"/> <code class="literal">java.lang.Boolean</code> </p></td></tr><tr><td style="text-align: left"><p> <a id="I_indexterm5_id690849" class="indexterm"/> <code class="literal">char</code> </p></td><td style="text-align: left"><p> <a id="I_indexterm5_id690868" class="indexterm"/> <code class="literal">java.lang.Character</code> </p></td></tr><tr><td style="text-align: left"><p> <a id="I_indexterm5_id690886" class="indexterm"/> <code class="literal">byte</code> </p></td><td style="text-align: left"><p> <a id="I_indexterm5_id690905" class="indexterm"/> <code class="literal">java.lang.Byte</code> </p></td></tr><tr><td style="text-align: left"><p> <a id="I_indexterm5_id690923" class="indexterm"/> <code class="literal">short</code> </p></td><td style="text-align: left"><p> <a id="I_indexterm5_id690941" class="indexterm"/> <code class="literal">java.lang.Short</code> </p></td></tr><tr><td style="text-align: left"><p> <a id="I_indexterm5_id690959" class="indexterm"/> <code class="literal">int</code> </p></td><td style="text-align: left"><p> <a id="I_indexterm5_id690978" class="indexterm"/> <code class="literal">java.lang.Integer</code> </p></td></tr><tr><td style="text-align: left"><p> <a id="I_indexterm5_id690996" class="indexterm"/> <code class="literal">long</code> </p></td><td style="text-align: left"><p> <a id="I_indexterm5_id691015" class="indexterm"/> <code class="literal">java.lang.Long</code> </p></td></tr><tr><td style="text-align: left"><p> <a id="I_indexterm5_id691032" class="indexterm"/> <code class="literal">float</code> </p></td><td style="text-align: left"><p> <a id="I_indexterm5_id691049" class="indexterm"/> <code class="literal">java.lang.Float</code> </p></td></tr><tr><td style="text-align: left"><p> <a id="I_indexterm5_id691067" class="indexterm"/> <code class="literal">double</code> </p></td><td style="text-align: left"><p> <a id="I_indexterm5_id691086" class="indexterm"/> <code class="literal">java.lang.Double</code> </p></td></tr></tbody></table></div></div><p>An instance of a wrapper class encapsulates a single value of its corresponding type. It’s an immutable object that serves as a container to hold the value and let us retrieve it later. You can construct a wrapper object from a primitive value or from a <code class="literal">String</code> representation of the value. The following statements are equivalent:</p><a id="I_5_tt253"/><pre class="programlisting"> <code class="n">Float</code> <code class="n">pi</code> <code class="o">=</code> <code class="k">new</code> <code class="n">Float</code><code class="o">(</code> <code class="mf">3.14</code> <code class="o">);</code> <code class="n">Float</code> <code class="n">pi</code> <code class="o">=</code> <code class="k">new</code> <code class="n">Float</code><code class="o">(</code> <code class="s">"3.14"</code> <code class="o">);</code></pre><p>The wrapper constructors throw a <a id="I_indexterm5_id691122" class="indexterm"/><code class="literal">NumberFormatException</code> when there is an error in parsing a string.</p><p>Each of the numeric type wrappers implements the <a id="I_indexterm5_id691136" class="indexterm"/><code class="literal">java.lang.Number</code> interface, which provides “value” methods access to its value in all the primitive forms. You can retrieve scalar values with the methods <code class="literal">doubleValue()</code>, <code class="literal">floatValue()</code>, <code class="literal">longValue()</code>, <code class="literal">intValue()</code>, <code class="literal">shortValue()</code>, and <code class="literal">byteValue()</code>:</p><a id="I_5_tt254"/><pre class="programlisting"> <code class="n">Double</code> <code class="n">size</code> <code class="o">=</code> <code class="k">new</code> <code class="n">Double</code> <code class="o">(</code> <code class="mf">32.76</code> <code class="o">);</code> <code class="kt">double</code> <code class="n">d</code> <code class="o">=</code> <code class="n">size</code><code class="o">.</code><code class="na">doubleValue</code><code class="o">();</code> <code class="c1">// 32.76</code> <code class="kt">float</code> <code class="n">f</code> <code class="o">=</code> <code class="n">size</code><code class="o">.</code><code class="na">floatValue</code><code class="o">();</code> <code class="c1">// 32.76</code> <code class="kt">long</code> <code class="n">l</code> <code class="o">=</code> <code class="n">size</code><code class="o">.</code><code class="na">longValue</code><code class="o">();</code> <code class="c1">// 32</code> <code class="kt">int</code> <code class="n">i</code> <code class="o">=</code> <code class="n">size</code><code class="o">.</code><code class="na">intValue</code><code class="o">();</code> <code class="c1">// 32</code></pre><p>This code is equivalent to casting the primitive <code class="literal">double</code> value to the various types.</p><p>The most common need for a wrapper is when you want to pass a primitive value to a method that requires an object. For example, in <a class="xref" href="ch11.html" title="Chapter 11. Core Utilities">Chapter 11</a>, we’ll look at the Java Collections API, a sophisticated set of classes for dealing with object groups, such as lists, sets, and maps. All the Collections APIs work on object types, so primitives must be wrapped when stored in them. We’ll see in the next section that Java makes this wrapping process automatic. For now, however, let’s do it ourselves. As we’ll see, a <code class="literal">List</code> is an extensible collection of <code class="literal">Object</code>s. We can use wrappers to hold numbers in a <code class="literal">List</code> (along with other objects):</p><a id="I_5_tt255"/><pre class="programlisting"> <code class="c1">// Simple Java code</code> <code class="n">List</code> <code class="n">myNumbers</code> <code class="o">=</code> <code class="k">new</code> <code class="n">ArrayList</code><code class="o">();</code> <code class="n">Integer</code> <code class="n">thirtyThree</code> <code class="o">=</code> <code class="k">new</code> <code class="n">Integer</code><code class="o">(</code> <code class="mi">33</code> <code class="o">);</code> <code class="n">myNumbers</code><code class="o">.</code><code class="na">add</code><code class="o">(</code> <code class="n">thirtyThree</code> <code class="o">);</code></pre><p>Here, we have created an <code class="literal">Integer</code> wrapper object so that we can insert the number into the <code class="literal">List</code>, using the <code class="literal">add()</code> method, which accepts an object. Later, when we are extracting elements from the <code class="literal">List</code>, we can recover the <code class="literal">int</code> value as follows:</p><a id="I_5_tt256"/><pre class="programlisting"> <code class="c1">// Simple Java code</code> <code class="n">Integer</code> <code class="n">theNumber</code> <code class="o">=</code> <code class="o">(</code><code class="n">Integer</code><code class="o">)</code><code class="n">myNumbers</code><code class="o">.</code><code class="na">get</code><code class="o">(</code><code class="mi">0</code><code class="o">);</code> <code class="kt">int</code> <code class="n">n</code> <code class="o">=</code> <code class="n">theNumber</code><code class="o">.</code><code class="na">intValue</code><code class="o">();</code> <code class="c1">// 33</code></pre><p>As we alluded to earlier, allowing Java to do this for us makes the code more concise and safer. The usage of the wrapper class is mostly hidden from us by the compiler, but it is still being used internally:<a id="I_indexterm5_id691283" class="indexterm"/></p><a id="I_5_tt257"/><pre class="programlisting"> <code class="c1">// Java code using autoboxing and generics</code> <code class="n">List</code><code class="o">&lt;</code><code class="n">Integer</code><code class="o">&gt;</code> <code class="n">myNumbers</code> <code class="o">=</code> <code class="k">new</code> <code class="n">ArrayList</code><code class="o">&lt;</code><code class="n">Integer</code><code class="o">&gt;();</code> <code class="n">myNumbers</code><code class="o">.</code><code class="na">add</code><code class="o">(</code> <code class="mi">33</code> <code class="o">);</code> <code class="kt">int</code> <code class="n">n</code> <code class="o">=</code> <code class="n">myNumbers</code><code class="o">.</code><code class="na">get</code><code class="o">(</code> <code class="mi">0</code> <code class="o">);</code></pre><p>This example will make more sense as you read the next section on <span class="emphasis"><em>autoboxing</em></span> and <span class="emphasis"><em>unboxing</em></span> of primitive values.<a id="I_indexterm5_id691311" class="indexterm"/><a id="I_indexterm5_id691318" class="indexterm"/><a id="I_indexterm5_id691325" class="indexterm"/></p></div><div class="sect2" title="Autoboxing and Unboxing of Primitives"><div class="titlepage"><div><div><h2 class="title"><a id="learnjava3-CHP-5-SECT-2.7"/>Autoboxing and Unboxing of Primitives</h2></div></div></div><p><a id="idx10220" class="indexterm"/> <a id="idx10221" class="indexterm"/> <a id="idx10230" class="indexterm"/> <a id="idx10246" class="indexterm"/> <a id="idx10256" class="indexterm"/> <a id="idx10262" class="indexterm"/>The Java compiler automatically wraps primitives in their wrapper types and unwraps them where appropriate. This process is called autoboxing and unboxing the primitive. It happens when primitives are used as arguments and return values in methods and on simple assignment to variables. For example:</p><a id="I_5_tt258"/><pre class="programlisting"> <code class="c1">// Simple assignments</code> <code class="n">Integer</code> <code class="n">integer</code> <code class="o">=</code> <code class="mi">5</code><code class="o">;</code> <code class="kt">int</code> <code class="n">i</code> <code class="o">=</code> <code class="k">new</code> <code class="n">Integer</code><code class="o">(</code><code class="mi">5</code><code class="o">);</code> <code class="c1">// Method arguments and return types</code> <code class="n">Double</code> <code class="nf">multiply</code><code class="o">(</code> <code class="n">Double</code> <code class="n">a</code><code class="o">,</code> <code class="n">Double</code> <code class="n">b</code> <code class="o">)</code> <code class="o">{</code> <code class="k">return</code> <code class="n">a</code><code class="o">.</code><code class="na">doubleValue</code><code class="o">()</code> <code class="o">*</code> <code class="n">b</code><code class="o">.</code><code class="na">doubleValue</code><code class="o">();</code> <code class="o">}</code> <code class="kt">double</code> <code class="n">d</code> <code class="o">=</code> <code class="n">multiply</code><code class="o">(</code> <code class="mf">5.0</code><code class="o">,</code> <code class="mf">5.0</code> <code class="o">);</code></pre><p>In the first case, Java simply wrapped the value 5 into an <code class="literal">Integer</code> for us. In the second case, it unwrapped our <code class="literal">Integer</code> object to its primitive value. Next, we have a method that multiplies two <code class="literal">Double</code> wrapper objects and returns the result as a <code class="literal">Double</code> wrapper. This example actually has three cases of boxing and one case of unboxing. First, the two double primitive values are boxed to <code class="literal">Double</code> types in order to call the method. Next, the return statement of the method is actually being called on a primitive double value, which the compiler turns into a <code class="literal">Double</code> before it leaves the method. Finally, the compiler unboxes the return value on assignment to the primitive double variable <code class="literal">d</code>.</p><div class="sect3" title="Performance implications of boxing"><div class="titlepage"><div><div><h3 class="title"><a id="learnjava3-CHP-5-SECT-2.7.1"/>Performance implications of boxing</h3></div></div></div><p><a id="I_indexterm5_id691479" class="indexterm"/>Gauging performance is tricky. For the vast majority of applications, the time it takes to perform tasks like creating a small object or calling a method is miniscule compared to other factors, such as I/O, user interaction, or the actual logic of the application. As a general rule, it’s not wise to worry too much about these detailed performance issues until the application is mature (no premature optimization). However, we can anticipate that allowing Java to box and unbox primitives in performance-critical areas will not be as fast as using primitives directly. One aspect of this to consider is how many new objects are being created and reclaimed by the garbage collector. While in general Java may be forced to create a new object for each boxed primitive, there are optimizations for a small range of values. Java guarantees that the Boolean values <code class="literal">true</code> and <code class="literal">false</code>, as well as “small” valued numeric types ranging from 0 to 127 for bytes and chars and from –128 to 127 for shorts and integers, are <a id="I_indexterm5_id691511" class="indexterm"/><span class="emphasis"><em>interned</em></span>. Saying that they are interned means that instead of creating a new object each time, Java reuses the same object on subsequent boxings. This is safe because primitive wrappers are immutable and cannot be changed.</p><a id="I_5_tt259"/><pre class="programlisting"> <code class="n">Integer</code> <code class="n">i</code> <code class="o">=</code> <code class="mi">4</code><code class="o">;</code> <code class="n">Integer</code> <code class="n">j</code> <code class="o">=</code> <code class="mi">4</code><code class="o">;</code> <code class="n">System</code><code class="o">.</code><code class="na">out</code><code class="o">.</code><code class="na">println</code><code class="o">(</code> <code class="n">i</code> <code class="o">==</code> <code class="n">j</code> <code class="o">);</code> <code class="c1">// This object equality is true only for small</code> <code class="c1">// values.</code></pre><p>The effect of this, as shown in this code snippet, is that for small identical values the boxed primitives are actually the same object. Java also attempts to intern string values in Java classes. We’ll talk about that in <a class="xref" href="ch10.html" title="Chapter 10. Working with Text">Chapter 10</a>.<a id="I_indexterm5_id691542" class="indexterm"/><a id="I_indexterm5_id691549" class="indexterm"/><a id="I_indexterm5_id691556" class="indexterm"/><a id="I_indexterm5_id691564" class="indexterm"/><a id="I_indexterm5_id691571" class="indexterm"/><a id="I_indexterm5_id691578" class="indexterm"/></p></div></div><div class="sect2" title="Variable-Length Argument Lists"><div class="titlepage"><div><div><h2 class="title"><a id="learnjava3-CHP-5-SECT-2.8"/>Variable-Length Argument Lists</h2></div></div></div><p><a id="idx10235" class="indexterm"/> <a id="idx10252" class="indexterm"/>As we mentioned earlier, Java methods may have <span class="emphasis"><em>variable-length argument lists</em></span> or “varargs” that allow them to take any number of arguments when invoked. The most common example usage of varargs is for the <a id="I_indexterm5_id691626" class="indexterm"/><code class="literal">printf()</code> style printing method, which allows any number of tags to be embedded in a string and takes an argument for each tag to be printed. For example:</p><a id="I_5_tt260"/><pre class="programlisting"> <code class="n">System</code><code class="o">.</code><code class="na">out</code><code class="o">.</code><code class="na">printf</code><code class="o">(</code><code class="s">"My name is %s and my age is %s\n"</code><code class="o">,</code> <code class="s">"Bob"</code><code class="o">,</code> <code class="mi">21</code> <code class="o">);</code> <code class="n">System</code><code class="o">.</code><code class="na">out</code><code class="o">.</code><code class="na">printf</code><code class="o">(</code><code class="s">"Get the %s out of %s before I %s\n"</code><code class="o">,</code> <code class="n">item</code><code class="o">,</code> <code class="n">place</code><code class="o">,</code> <code class="n">action</code> <code class="o">);</code></pre><p>Varargs allow the <code class="literal">printf()</code> method to accept any number of items to print (from zero to dozens, as awkward as that would be).</p><p>A method accepting a variable argument list is equivalent to a method accepting an array of some type of object. The difference is that the compiler makes the method call accept individual, comma-separated values, and then packs them into the array for us. The syntax for declaring the varargs method uses ellipses (<code class="literal">...</code>) where the square brackets of an array might go. For example:</p><a id="I_5_tt261"/><pre class="programlisting"> <code class="kt">void</code> <code class="nf">printObjects</code><code class="o">(</code> <code class="n">Object</code> <code class="o">...</code> <code class="n">list</code> <code class="o">)</code> <code class="o">{</code> <code class="c1">// list is an Object []</code> <code class="k">for</code><code class="o">(</code> <code class="n">Object</code> <code class="n">o</code> <code class="o">:</code> <code class="n">list</code> <code class="o">)</code> <code class="n">System</code><code class="o">.</code><code class="na">out</code><code class="o">.</code><code class="na">println</code><code class="o">(</code> <code class="n">o</code> <code class="o">);</code> <code class="o">}</code></pre><p>Inside the <code class="literal">printObjects()</code> method, the variable <code class="literal">list</code> is actually an <code class="literal">Object []</code> type. We could find out how many arguments were passed to us by asking the array for its length in the usual way:</p><a id="I_5_tt262"/><pre class="programlisting"> <code class="n">System</code><code class="o">.</code><code class="na">out</code><code class="o">.</code><code class="na">println</code><code class="o">(</code> <code class="s">"Number of arguments:"</code> <code class="o">+</code> <code class="n">list</code><code class="o">.</code><code class="na">length</code> <code class="o">);</code></pre><p>If the caller passed no arguments, the array will be empty.</p><p>In the case of our <code class="literal">printObjects()</code> method, we could pass a mix of primitive values as well as object types because the compiler would automatically box the primitives to their wrapper types for us before placing them into the <code class="literal">Object []</code>.</p><p>The variable argument list does not have to be of type <code class="literal">Object</code>. It can be of any type, including primitive types. For example:</p><a id="I_5_tt263"/><pre class="programlisting"> <code class="n">printInts</code><code class="o">(</code> <code class="kt">int</code> <code class="o">...</code> <code class="n">list</code> <code class="o">)</code> <code class="o">{</code> <code class="c1">// list is an int []</code> <code class="o">}</code> <code class="c1">// usage</code> <code class="n">printInts</code><code class="o">(</code> <code class="mi">1</code><code class="o">,</code> <code class="mi">2</code><code class="o">,</code> <code class="mi">3</code><code class="o">,</code> <code class="mi">4</code> <code class="o">);</code> <code class="n">printStrings</code><code class="o">(</code> <code class="n">String</code> <code class="o">...</code> <code class="n">list</code> <code class="o">)</code> <code class="o">{</code> <code class="c1">// list is a String []</code> <code class="o">}</code> <code class="c1">// usage</code> <code class="n">printStrings</code><code class="o">(</code> <code class="s">"foo"</code><code class="o">,</code> <code class="s">"bar"</code><code class="o">,</code> <code class="s">"gee"</code> <code cl