views:

196

answers:

5

how can i write a query controlled loop that will continue to input int values from the user,adding each to the value sum,and then ask if the user has another value to input,until the user says that there are no more values

+3  A: 
double sum = 0;
while (user.hasMoreInput()) {
    double += user.mostRecentInput();
}

where you implement hasMoreInput and mostRecentInput to your likening.

Adrian
Hehe, nice. +1 :)
Bombe
Exact. Mapping requirements to code is so damn easy :)
Andreas_D
A: 

The Java Developer's Almanac is always a good source of basic examples such as yours.

 BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
 String str = "";
 while (str != null) {
     System.out.print("> prompt ");
     str = in.readLine();
     process(str);
 }

Edit: Apparently some people think that a demonstration of the essentials of some technique should have error-checking. Perhaps I should also have commented the code, and provided a spec. Next time, I'll also develop some custom annotations to express pre and post conditions, or draft an implementation in Eiffel.

Jonathan Feinberg
+1: Good answer, thanks for the link! But I urge readers to code something useful in the `catch` block. All kinds of user frustration results from this reprehensible practice of swallowing exceptions. I'd say code like this shouldn't appear in an Almanac; it wouldn't have hurt them to include an extra line of code.
Carl Smotricz
No, I take that back. The code is horrible! `readLine()` is followed by `process(str)` without a null check. People who code like this have no business writing almanacs.
Carl Smotricz
That's a very weird way of doing a REPL - you're going to process a null string when you reach EOF. More idiomatic usage would be something like `prompt(); for (String cmd; (cmd = in.readLine()) != null; ){ process(cmd); prompt(); }`
gustafc
Jonathan, we're not criticising *your* code, but the "Almanac" code, which should rightly be held to higher standards. Error checking can be considered optional, especially in a demo; but allowing a program to explode on EOF is unacceptable.
Carl Smotricz
maybe `process()` can deal with `null`... or even need it to signal the EOF... OK, would be bad practice and misleading.
Carlos Heuberger
+1  A: 

This is how I write such a loop. I shouldn't be writing your homework for you, but I would nevertheless like to demonstrate my favorite style for this kind of loop.

BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
while (true) {
    System.out.print("> prompt ");
    String str = in.readLine();
    if (str == null) break;
    process(str);
}

Some people may not like

  • while (true) - it looks like an infinite loop because it is! It's as infinite as the user's patience in typing input.
  • Single-line if - some people would prefer to make this a fully bracketed 3-liner. But I don't see any use in that; it doesn't become more readable as a result.
  • break in mid-loop. That's what break is for! It's your escape hatch from otherwise infinite loops.

If you're used to reading Java code, this is idiomatic and legible. Advantages:

  • It shows steps happening in exactly the sequence they happen;
  • It limits the scope of str to exactly where it's needed;
  • It's very explicit about the termination condition;
  • It's very concise. Fewer lines = fewer bugs, I always say.
Carl Smotricz
A: 

There are a few pieces you need to handle. First, you need to know how to receive input from the user. The Java Developer's Almanac example (http://www.exampledepot.com/egs/java.io/ReadFromStdIn.html) that I found looks like this:

try {
        BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
        String str = "";
        while (str != null) {
            System.out.print("> prompt ");
            str = in.readLine();
            process(str);
        }
    } catch (IOException e) {
}

You might replace "> prompt" with something more descriptive. You'd also like to have a better way for the user to quit than entering a blank line, so maybe ask them to enter a 'q' if they are done. Then, change the comparison in the while loop to something like !str.toLowerCase().equals("q"). Then, you need to implement the process function to convert the string to an integer. Integer.parseInt(String) will return the integer value of a String that correctly represents an integer (ie, "3" or "49" but not "7e") and will throw a NumberFormatException otherwise. Because you don't want your application to fail with an exception on bad input, I think that process could just return 0 in the event of a non-Integer String (ie, when you catch a NumberFormatException).

Finally, you will want to have a sum variable initialized before your main loop, and you could add the result of process during each iteration. Then when the loop is over, you can print the result of process to the screen using System.out.println.

I purposely left out most of the code because this does sound like homework, but if you can understand all this enough to put it together I think you'll have learned it well enough to do it on your own.

danben
empty catch? at least do a printStackTrace! or don't catch at all... the worse is to hide the error as done above.
Carlos Heuberger
This code is just copied verbatim from that link, as I mentioned above. And the catch statement is not missing its close brace, it just isn't indented.
danben
haven't said anything about missing close brace...
Carlos Heuberger
No, you didn't. Someone commented after you and then deleted it when I corrected him.
danben
A: 

This is how I typically do it. as little code as possible :).

String s;
BufferedReader in = new BufferedReader(new InputStreamReader(System.in));
while((s = in.readLine()) != null)
    process(s);
Omry
not "as little as possible", won 2 lines : `while (process(in.readLine()));` .... (not saying that I would do it that way)
Carlos Heuberger
well, you will need to have an if (s != null) inside process, so it's not clear if your version is really shorter.
Omry
was meant to be a joke, but I still don't need the `String s;` line, and most probably I would have a check (empty String) or at least an assert in process... :-)
Carlos Heuberger