1.
for (int i = 0; (boolean)true; i++) {
}
2.
for (int i = 0; (boolean)false; i++) {
}
3.
boolean t=false;
for (int i = 0; t; i++) {
}
The first for loop compiles & runs, but the second for loop compilation fails with error. It says Unreachable Statement. And the third for loop compiles & runs.
The first loop is infinite loop. Since the condition is always true, and will always be satisfied.
It's like writing:
int i=0;
while(true)
i++;
As you can see, the condition is always true and nothing changes this true.
The second loop is Unreachable code since the piece of code below this loop will never be reached (false is always false and you never change it). So it's redundant.
See Chapter 14.21. Unreachable Statements
Since Java knows that the programmer is human :) it notifies you about this to prevent mistakes.
Note that while(false) or the second loop you have differ from if(false)... since while(false) (or the loop you have) doesn't make sense because the code below it will no be execute. Not like if(false) that might have else, so the compiler doesn't complain about it in this case.
Regarding the OP update:
In the third case there will be no compilation error since the false value is assigned to the variable and in this case, the variable can be re-assigned to have true value in it. So the compiler doesn't arise an error.
Note that if the variable is declared as final then the compiler will arise an error since this variable can be never assigned to a new value, thus the code below the for loop will be unreachable.
for (int i = 0; <This_has_to_be_true>; i++)
The second part of the for loop has to be true for the loop to execute. Since you're manually setting it to be always fase, the loop will never run, hence the code inside it is unreachable.
The compiler is telling you the code inside the second loop (even if empty) will never be reached and executed, because the condition is always false.
BTW, why are you trying to do this anyway?
In the second for loop, the condition is always false so the for block (even if is empty) will never be executed (it is unreacheable).
Like in this case :
if (false) {
}
Related
I have a program I need to implement that has the following code:
for (int n = 1024; true; n+=n)
I cannot find any other examples of java loops having such a format. What does this mean? I've tried to research it, but I don't even know what to search for - it's totally foreign to me.
The basic for statement is described in the language spec:
for ( [ForInit] ; [Expression] ; [ForUpdate] ) Statement
You are asking about the case when Expression is true. (The square brackets above mean it is optional).
The meaning of that is described just below, in Sec 14.14.1.2:
If the Expression is not present, or it is present and the value resulting from its evaluation (including any possible unboxing) is true, then the contained Statement is executed.
...
If the Expression is present and the value resulting from its evaluation (including any possible unboxing) is false, no further action is taken and the forstatement completes normally.
So, Expression is present, and evaluates to true (because true evaluates to true). Hence, Statement is executed, and will continue to be executed because Expression remains true.
As such, it is an infinite loop (unless there is a break, return, throw or System.exit inside the loop).
Why you dont use another loop? Use for example do-while instead of
for (int n = 1024; true; n+=n)
You can make a work around with:
int n=1024;
do{
//your code
n+=n;
}while(condition==false);
I've started to learn java, and in some examples I've seen special for loop (not very familiar to me). It's not enhanced for loop, but it looks like this
for(;;i++){ do something..}
I don't know what it means, when I just have these semicolons o.O If someone could explain it to me, would be grateful.
I would read through this: https://docs.oracle.com/javase/tutorial/java/nutsandbolts/for.html
As you might notice,
The general form of the for statement can be expressed as follows:
for (initialization; termination;
increment) {
statement(s)
}
...
The three expressions of the for loop are optional; an infinite loop can be created as follows:
// infinite loop
for ( ; ; ) {
// your code goes here
}
(emphasis mine)
In your example, I would expect the variable i would have been declared and initialized before the for loop. If there is no termination condition, the loop will run infinitely.
You can also have a termination condition inside a loop, something like :
if(i = some number) {break;} //this will break the loop
Similarly, the increment statement can also be declared inside a loop.
I'm reading a Java book and I came across an interesting for loop. It looks like this:
for(; (j>0) && (tmp < a[j-1]); j--)
I understand that (j>0) && (tmp < a[j-1]) is the condition check and j-- is the decrease of the variable. However, I don't get where's the initialization statement.
There is no initialization statement in your example. It's optional.
j is probably declared and initialized before the loop.
Normally, you would initialize j in the first statement in the for loop (which is empty here) since it is a looping index and is usually only used inside the loop. Also the standard syntax for Java for loops is for( initialization; termination condition; increment), but the language only enforces that there be three statements (with the middle one being a boolean expression) , so you can have three empty statements for(;;) which creates an infinite loop or you could put some other statement in there (except for the middle expression where a boolean expression is expected) like for(System.out.println("I was supposed to initialize here"); false && true; logger.log("Nope.")). OF course, you shouldn't do that, but it is legal.
Note: Some statements would be illegal if put in place of the third statement as well, like variable declarations, since it is executed at the end of each iteration (see this for more on legal for loop syntax)
I like to think of for loops as a shorthand for a common form of the while loop, where you want to loop a number of times:
int i= 0; // Initialization
while (i< max){ // termination
// Do stuff
i++; // increment
}
which is helpful for understanding what it does with these statements.
for(initialization; condition; increment)
None of them are a must to declare a for loop. You can have a for loop like for(;;) if you want. It will compile without any errors.
According to your question j have been already initialized some where. Therefore it is perfectly fine.
When executing a while loop, does java constantly check if the parameter(s) are true? For example if a while loop is
while(k=7) {
Thread.sleep(5000);
}
but during the 5 seconds another thread changes k to 8, would the loop continue waiting or exit immediately?
No, it will only check when the execution path takes it there. Thus, it will check every 5 seconds in your example.
If you wanted to be notified immediately, you would have to use wait(), notify(), or some other synchronization method.
Here is an example
No. Even if k were volatile (or, worse, changed from another thread without you making it volatile; bad idea) or an object whose properties could change via the methods called inside the loop, it will only be checked at the end of the loop body, deciding to repeat the body or continue past the loop.
You can break out of the loop by interrupting the thread and having the catch outside the loop, or with an internal check and break.
The condition is checked once at the start and, if the loop is entered, once after the execution of the body on each iteration. So no, it will not exit immediately, even if k is altered while the body is being executed.
Oh, and you probably meant k == 7 (recall that == compares while = assigns). Some will even write 7 == k to avoid potentially making this mistake.
This doesn't really have much to do with threads. For instance, consider:
int k = 7;
while (k == 7) {
k = 8;
System.out.println("here!");
}
here!
Notice how the body is still fully executed even though k is immediately changed to a value that no longer satisfies the loop condition.
I had an if statement checking some value, And encountered a weird bug(Not sure!). My code was incorrect syntactically and in result it produced a wrong result, however eclipse didn't raised any error while compiling. Why My below code worked?
if((this.trackPointList.get(point).getTurnOutId().equals(seg.getSegRef().getTurnOut())) && seg.getSegRef().getKind().equals("arc")); // <---- See here I have semicolon
{
... code to run ...
}
Above code check only first condition and ignores seg.getSegRef().getKind().equals("arc") but I guess this should raised an issue at compile time, Am I right? My logic worked once I debugged it by skimming line by line and found this semicolon. I will appreciate if someone could explain, if it is a valid syntax.
Enlighten Me, Please!
The ; makes Java think that the body of the if conditional is complete, even if there is no other code preceding it. In effect, the code in the if statement is executed, but no body exists because the ; is there.
The { ...code to run...} is just a code block that executes, and anything declared inside that block is not visible outside the block. It will always run here because it's not part of the if block.
edit: here's another stack overflow question about the { } blocks: What do curly braces in Java mean by themselves?
The code is syntactically correct. You can write ifs without braces, like:
if(condition) statement;
Having empty statements is also valid. For instance this code is valid:
int a = 0;;
;;;
So an empty if is valid as well, although it doesn't make much sense :)
if(condition);
An if statement followed by a semicolon is called an "empty if statement".
It rarely is of any use, but it's syntactically legal.
You can write something like this
if ( doSomethingThatReturnsABoolean() )
; // Empty statement
else
doSomeOtherThing()
but it would be better to write
if ( !doSomethingThatReturnsABoolean() )
doSomeOtherThing()
Regarding your observation that only the first condition gets checked:
If the first condition returns false the second condition will not get checked, because
(false && secondCondition)
always equals to false, so the value of secondCondition is irrelevant.
The ; after the if(..) statement represents an empty statement that is executed conditionally when the if(..) evaluates to true. The { .. } represents a code block that always executes with it's own scope.
The second condition may be ignored if the first condition is false due to short-circuit evaluation.
if(condition); is equivalent to if(condition){}
same thing with for loop & while loop:
for(;condition;); is equivalent to for(;condition;){}
while(condition); is equivalent to while(condition){}