Thinking in Java - 4th Edition
1079 pág.

Thinking in Java - 4th Edition

Disciplina:Programação Orientada a Objetos1.253 materiais31.988 seguidores
Pré-visualização50 páginas
in a string:

Controlling Execution 97 

//: control/ForEachString.java
public class ForEachString {
 public static void main(String[] args) {
 for(char c : "An African Swallow".toCharArray() )
 System.out.print(c + " ");
 }
} /* Output:
A n A f r i c a n S w a l l o w
*///:~

As you’ll see in the Holding Your Objects chapter, foreach will also work with any object that
is Iterable.

Many for statements involve stepping through a sequence of integral values, like this:

for(int i = 0; i < 100; i++)

For these, the foreach syntax won’t work unless you want to create an array of int first. To
simplify this task, I’ve created a method called range( ) in net.mindview.util.Range that
automatically generates the appropriate array. My intent is for range( ) to be used as a
static import:

//: control/ForEachInt.java
import static net.mindview.util.Range.*;
import static net.mindview.util.Print.*;
public class ForEachInt {
 public static void main(String[] args) {
 for(int i : range(10)) // 0..9
 printnb(i + " ");
 print();
 for(int i : range(5, 10)) // 5..9
 printnb(i + " ");
 print();
 for(int i : range(5, 20, 3)) // 5..20 step 3
 printnb(i + " ");
 print();
 }
} /* Output:
0 1 2 3 4 5 6 7 8 9
5 6 7 8 9
5 8 11 14 17
*///:~

The range( ) method has been overloaded, which means the same method name can be
used with different argument lists (you’ll learn about overloading soon). The first overloaded
form of range( ) just starts at zero and produces values up to but not including the top end
of the range. The second form starts at the first value and goes until one less than the second,
and the third form has a step value so it increases by that value. range( ) is a very simple
version of what’s called a generator, which you’ll see later in the book.

Note that although range( ) allows the use of the foreach syntax in more places, and thus
arguably increases readability, it is a little less efficient, so if you are tuning for performance
you may want to use a profiler, which is a tool that measures the performance of your code.

You’ll note the use of printnb( ) in addition to print( ). The printnb( ) method does not
emit a newline, so it allows you to output a line in pieces.

98 Thinking in Java Bruce Eckel

The foreach syntax not only saves time when typing in code. More importantly, it is far easier
to read and says what you are trying to do (get each element of the array) rather than giving
the details of how you are doing it (“I’m creating this index so I can use it to select each of the
array elements.”). The foreach syntax will be used whenever possible in this book.

return
Several keywords represent unconditional branching, which simply means that the branch
happens without any test. These include return, break, continue, and a way to jump to a
labeled statement which is similar to the goto in other languages.

The return keyword has two purposes: It specifies what value a method will return (if it
doesn’t have a void return value) and it causes the current method to exit, returning that
value. The preceding test( ) method can be rewritten to take advantage of this:

//: control/IfElse2.java
import static net.mindview.util.Print.*;
public class IfElse2 {
 static int test(int testval, int target) {
 if(testval > target)
 return +1;
 else if(testval < target)
 return -1;
 else
 return 0; // Match
 }
 public static void main(String[] args) {
 print(test(10, 5));
 print(test(5, 10));
 print(test(5, 5));
 }
} /* Output:
1
-1
0
*///:~

There’s no need for else, because the method will not continue after executing a return.

If you do not have a return statement in a method that returns void, there’s an implicit
return at the end of that method, so it’s not always necessary to include a return statement.
However, if your method states it will return anything other than void, you must ensure
every code path will return a value.

Exercise 6: (2) Modify the two test( ) methods in the previous two programs so that
they take two extra arguments, begin and end, and so that testval is tested to see if it is
within the range between (and including) begin and end.

break and continue
You can also control the flow of the loop inside the body of any of the iteration statements by
using break and continue. break quits the loop without executing the rest of the
statements in the loop. continue stops the execution of the current iteration and goes back
to the beginning of the loop to begin the next iteration.

Controlling Execution 99 

This program shows examples of break and continue within for and while loops:

//: control/BreakAndContinue.java
// Demonstrates break and continue keywords.
import static net.mindview.util.Range.*;
public class BreakAndContinue {
 public static void main(String[] args) {
 for(int i = 0; i < 100; i++) {
 if(i == 74) break; // Out of for loop
 if(i % 9 != 0) continue; // Next iteration
 System.out.print(i + " ");
 }
 System.out.println();
 // Using foreach:
 for(int i : range(100)) {
 if(i == 74) break; // Out of for loop
 if(i % 9 != 0) continue; // Next iteration
 System.out.print(i + " ");
 }
 System.out.println();
 int i = 0;
 // An "infinite loop":
 while(true) {
 i++;
 int j = i * 27;
 if(j == 1269) break; // Out of loop
 if(i % 10 != 0) continue; // Top of loop
 System.out.print(i + " ");
 }
 }
} /* Output:
0 9 18 27 36 45 54 63 72
0 9 18 27 36 45 54 63 72
10 20 30 40
*///:~

In the for loop, the value of i never gets to 100 because the break statement breaks out of
the loop when i is 74. Normally, you’d use a break like this only if you didn’t know when the
terminating condition was going to occur. The continue statement causes execution to go
back to the top of the iteration loop (thus incrementing i) whenever i is not evenly divisible
by 9. When it is, the value is printed.

The second for loop shows the use of foreach, and that it produces the same results.

Finally, you see an “infinite” while loop that would, in theory, continue forever. However,
inside the loop there is a break statement that will break out of the loop. In addition, you’ll
see that the continue statement moves control back to the top of the loop without
completing anything after that continue statement. (Thus printing happens in the second
loop only when the value of i is divisible by 10.) In the output, the value 0 is printed, because
0 % 9 produces 0.

A second form of the infinite loop is for(;;). The compiler treats both while(true) and
for(;;) in the same way, so whichever one you use is a matter of programming taste.

Exercise 7: (1) Modify Exercise 1 so that the program exits by using the break keyword
at value 99. Try using return instead.

100 Thinking in Java Bruce Eckel

The infamous “goto”
The goto keyword has been present in programming languages from the beginning. Indeed,
goto was the genesis of program control in assembly language: “If condition A, then jump
here; otherwise, jump there.” If you read the assembly code that is ultimately generated by
virtually any compiler, you’ll see that program control contains many jumps (the Java
compiler produces its own “assembly code,” but this code is run by the Java Virtual Machine
rather than directly on a hardware CPU).

A goto is a jump at the source-code level, and that’s what brought it into disrepute. If a
program will always jump from one point to another, isn’t there some way to reorganize the
code so the flow of control is not so jumpy? goto fell into true disfavor with the publication
of the famous “Goto considered harmful” paper by Edsger Dijkstra, and since then goto-
bashing has been a popular sport, with advocates of the cast-out keyword scurrying for cover.

As