常见的循环逻辑
In the following sections, we discuss some of the most common algorithms that are implemented as loops. You can use them as starting points for your loop designs.
Sum and Average Value
Computing the sum of a number of inputs is a very common task. Keep a running total, a variable to which you add each input value. Of course, the total should be initialized with 0.
double total = 0;
while (in.hasNextDouble())
{
double input = in.nextDouble();
total = total + input;
}
Note that the total variable is declared outside the loop. We want the loop to update a single variable. The input variable is declared inside the loop. A separate variable is created for each input and removed at the end of each loop iteration.
To compute an average, count how many values you have, and divide by the count. Be sure to check that the count is not zero.
double total = 0;
int count = 0;
while (in.hasNextDouble())
{
double input = in.nextDouble();
total = total + input;
count++;
}
double average = 0;
if (count > 0)
{
average = total / count;
}
Counting Matches
You often want to know how many values fulfill a particular condition. For example, you may want to count how many spaces are in a string. Keep a counter, a variable that is initialized with 0 and incremented whenever there is a match.
int spaces = 0;
for (int i = 0; i < str.length(); i++)
{
char ch = str.charAt(i);
if (ch == ' ')
{
spaces++;
}
}
For example, if str is "My Fair Lady", spaces is incremented twice (when i is 2 and 7).
Note that the spaces variable is declared outside the loop. We want the loop to update a single variable. The ch variable is declared inside the loop. A separate variable is created for each iteration and removed at the end of each loop iteration.
This loop can also be used for scanning inputs. The following loop reads text, a word at a time, and counts the number of words with at most three letters:
int shortWords = 0;
while (in.hasNext())
{
String input = in.next();
if (input.length() <= 3)
{
shortWords++;
}
}
Finding the First Match
When you count the values that fulfill a condition, you need to look at all values. However, if your task is to find a match, then you can stop as soon as the condition is fulfilled.
Here is a loop that finds the first letter A in a string. Because we do not visit all elements in the string, a while loop is a better choice than a for loop:
boolean found = false;
char ch = '?';
int position = 0;
while (!found && position < str.length())
{
ch = str.charAt(position);
if (ch == 'A' || ch == 'a') { found = true; }
else { position++; }
}
If a match was found, then found is true, ch is the first matching character, and position is the index of the first match. If the loop did not find a match, then found remains false after the end of the loop.
Note that the variable ch is declared outside the while loop because you may want to use the input after the loop has finished. If it had been declared inside the loop body, you would not be able to use it outside the loop.
Prompting Until a Match is Found
In the preceding example, we searched a string for a character that matches a condition. You can apply the same process to user input. Suppose you are asking a user to enter a positive value < 100. Keep asking until the user provides a correct input:
boolean valid = false;
double input = 0;
while (!valid)
{
System.out.print("Please enter a positive value < 100: ");
input = in.nextDouble();
if (0 < input && input < 100) { valid = true; }
else { System.out.println("Invalid input."); }
}
Note that the variable input
is declared outside the while loop because you will want to use the input after the loop has finished.
Maximum and Minimum
To compute the largest value in a sequence, keep a variable that stores the largest element that you have encountered, and update it when you find a larger one.
double largest = in.nextDouble();
while (in.hasNextDouble())
{
double input = in.nextDouble();
if (input > largest)
{
largest = input;
}
}
This algorithm requires that there is at least one input.
To compute the smallest value, simply reverse the comparison:
double smallest = in.nextDouble();
while (in.hasNextDouble())
{
double input = in.nextDouble();
if (input < smallest)
{
smallest = input;
}
}
Comparing Adjacent Values
When processing a sequence of values in a loop, you sometimes need to compare a value with the value that just preceded it. For example, suppose you want to check whether a sequence of inputs contains adjacent duplicates such as:
1 7 2 9 9 4 9
Now you face a challenge. Consider the typical loop for reading a value:
double input;
while (in.hasNextDouble())
{
input = in.nextDouble();
. . .
}
How can you compare the current input with the preceding one? At any time, input contains the current input, overwriting the previous one.
The answer is to store the previous input:
double input = 0;
while (in.hasNextDouble())
{
double previous = input;
input = in.nextDouble();
if (input == previous)
{
System.out.println("Duplicate input");
}
}
One problem remains. When the loop is entered for the first time, input has not yet been read. You can solve this problem with an initial input operation outside the loop:
double input= in.nextDouble();
while (in.hasNextDouble())
{
double previous = input;
input = in.nextDouble();
if (input == previous)
{
System.out.println("Duplicate input");
}
}
Here is a program that demonstrates common loop algorithms.
import java.util.Scanner;
/**
This program combines several common loop algorithms.
*/
public class LoopAlgorithms
{
public static void main(String[] args)
{
Scanner in = new Scanner(System.in);
System.out.print("Enter input: ");
int input = in.nextInt();
int min = input; // The largest input
int max = input; // The smallest input
int count = 1; // The number of inputs
int sum = input; // The sum of the inputs
boolean foundNegative = false;
// Set to true if we found at least one negative input
int negatives; // The count of negative inputs
int firstNegative = 0; // The position of the first negative input
if (input < 0)
{
foundNegative = true;
firstNegative = 1;
negatives = 1;
}
else
{
negatives = 0;
}
boolean done = false;
while (!done)
{
System.out.print("Enter input, 0 to quit: ");
input = in.nextInt();
if (input == 0) // Zero is the sentinel value
{
done = true;
}
else
{
sum = sum + input; // Computing sum and average
count++;
if (input < min) // Determining minimum and maximum
{
min = input;
}
else if (input > max)
{
max = input;
}
if (input < 0) // Counting matches
{
negatives++;
if (!foundNegative) // Finding first match
{
foundNegative = true;
firstNegative = count;
}
}
}
}
System.out.println("Minimum: " + min);
System.out.println("Maximum: " + max);
System.out.println("Sum: " + sum);
System.out.println("Average: " + sum * 1.0 / count);
System.out.println("Negative values: " + negatives);
if (foundNegative)
{
System.out.println("First negative: " + firstNegative);
}
}
}
评论已关闭