Page 1 of 1

About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Wed Apr 26, 2017 3:30 am
by Javier
Hi Paul!
I have a doubt!
I would like to know if with the final classes like String, when we do this:
String s=new String("a");
s=s+"b"; // s is pointing to new value, but is it pointing to new object?
and...
String s= "a";// we don´t have a String object, do we? it is just a literal value?
Thank you in advance Paul!

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Wed Apr 26, 2017 3:52 am
by admin
First, there is an important thing that you need to know about strings in Java. All strings are Java objects of class java.lang.String. In other words, they are all instances of class java.lang.String.

Unlike int, char, boolean etc., strings are not primitives. So there is no difference between a String value and a String object. String value is nothing but a String object. So yes, when you do s = s+"b", a new String object containing "ab" is created.

Since strings are used so much in a program, Java has provided a short cut for creating strings. You can create String objects by just putting the value in double quotes instead of doing new String. This is has nothing do to with String class being final class. It is the same String class object that is created whether you use the new String syntax or just the double quotes.

But there is one big difference between creating a String object using "" and creating a String object using new String. This difference is explained in detail here : http://stackoverflow.com/questions/1057 ... -interning

HTH,
Paul.

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Wed Apr 26, 2017 4:28 am
by Javier
Thank you Paul! I got it now!
One question more,
public static double calc (double value){
int coupon, offset, base; // these are local variables, and we should initialize before use them, ok.
return coupon*offset*base*value/100;/* "value" is the argument of the parameter, and if I am right, value is a local variable as well, my question is why value is compiling if we are use it before initialize it? so in this case, only matters the local variables declared in the body?
*/
}
I think that I am missing something important...
Thank you Paul

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Wed Apr 26, 2017 5:16 am
by admin
No one can call the method calc without passing an argument. So the value variable will always be already initialized inside the method. Therefore, there is no point in initializing it.

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Wed Apr 26, 2017 5:39 am
by Javier
Thank you so much Paul, I didn´t see that!!

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Fri Jun 09, 2017 9:56 am
by yrelhan
"Had percent been defined as final ( static final double percent = 0; ), the code would work and print 3000.0."

Why is that?

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Fri Jun 09, 2017 10:05 am
by admin
Did you read the explanation? It explains exactly what you are asking. Please let me know which part is not clear so that I can elaborate.

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Thu Jun 15, 2017 7:05 am
by JavaSoftware
"Had percent been defined as final ( static final double percent = 0; ), the code would work and print 3000.0."

Why is that?
I think compiler knows that " static final double percent = 0; " will be available at compile time and will put 0 inside if statement and will exactly know that will be true and the local variables will be initialized before the return statement, hope i'm correct :)

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Thu Jun 15, 2017 7:29 am
by admin
That is correct :)

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Thu Dec 27, 2018 12:20 pm
by crazymind
Hi, I don't understand this question. Why does not error happens at line 3?

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Thu Dec 27, 2018 12:26 pm
by admin
why do you think there should be an error at //3?

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Thu Dec 27, 2018 5:57 pm
by crazymind
int coupon, offset, base; should follow by initialization to those variables.I don't understand why compiler can not read the initialization inside the if statement. Can you please explain how compiler deal with this situation? thanks!

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Thu Dec 27, 2018 9:35 pm
by admin
There is no problem if you just declare a variable without initializing it. The problem occurs when you try to use that uninitialized variable.

Remember that compiler does not execute any code. So, it does not know the result of evaluation of if condition (evaluation happens at run time). So, it does not know that the variables coupon, offset, and base actually will be initialized.

That is why the error is at //5 and not at //3.

Make percent variable final and then see what happens.

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Thu Mar 11, 2021 10:49 am
by f.motta
Hi
Thanks for the great explanation so far!
I get the logic of this question.

But the following code doesn't should work similarly??

Code: Select all

class Bond  {
    final static int price = 5;
    public boolean sell() {
        if(price<10) {
            return true;
        } 
    }       // DOES NOT COMPILE!!! MISSING RETURN STATEMENT
I know that is different because the return is within the if body. But similarly it is guarantee that price<10 will be true since price is defined as final, and so the return statement will execute.

Thanks in advance!
Felipe Motta

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Fri Mar 12, 2021 12:34 am
by admin
Filipe, in your example, it is true that price is final and price is < 10. However, you have to understand that compiler cannot execute the code. So, it cannot evaluate the value of the expression price<10. While reading the code, we (humans) evaluate the expression intuitively and know that this must always be true but the compiler does not do so. It's job is only to look for information that is available at compile time and then make decisions based on it.
Similarly, the compiler cannot evaluate an if statement either even if the value in the if condition is a compile time constant.

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Fri Apr 29, 2022 11:12 am
by skreber
Dear all,
I have the same question as f.motta.

It was also my understanding that the compiler does not execute code.

(1)
Her example given conforms to this: price<10 does not get executed when compiling, so compilation fails due to the missing return method:

Code: Select all

class Bond  {
    final static int price = 5;
    public boolean sell() {
        if(price<10) {
            return true;
        } 
    }       // DOES NOT COMPILE!!! MISSING RETURN STATEMENT
(2) However, I do not understand why in the original exam question's explanation solution,

Code: Select all

static final double percent = 0; 
solves a similar problem (by making percent final), and suddenly the compiler DOES seem to execute percent <10, enters the IF, sees the initialization of the so far uninitialized variables, and therefore does not complain upon

Code: Select all

 return coupon*offset*base*value/100; //5 
that they are uninitialized anymore.
Why does it peek inside percent <10 (original exam question) and not in price<10 (f.motta's example)? In both cases, there's a static final variable who's being evaluated in an IF, and code outside that IF that should not compile (possibly uninitialized variables being used VS nothingness, i.e. lacking missing statement).

Why has making the static variable (used in the IF condition) final solved the compiler error in the exam Q case but not in f.motta's case?

Can the compiler peek inside the IF if the condition has a constant and detect an initialization, but not a return statement?

Re: About Question enthuware.ocajp.i.v8.2.1421 :

Posted: Fri Apr 29, 2022 11:38 pm
by admin
As per JLS Section 8.4.7 Method body:
If a method is declared to have a return type (§8.4.5), then a compile-time error occurs if the body of the method can complete normally (§14.1).

In other words, a method with a return type must return only by using a return statement that provides a value return; the method is not allowed to "drop off the end of its body". See §14.17 for the precise rules about return statements in a method body.
So, I think you are right in saying that in both the cases the compiler should allow compilation. But the fact is that it allows one but not the other. It could either be a lacuna in the implementation of the compiler or it could be a result of giving more precedence to the above mentioned rule given in 8.4.7.

Only the language designers/compiler implementers can tell for sure.

HTH,
Paul.