Link to home
Start Free TrialLog in
Avatar of gksinghiet
gksinghiet

asked on

Initialization of local reference variable

In a java class if you have not initialize a local reference variable before using it, the compiler throws exception.
But when you explicitly initialize it with null it didn't complain. Why is it so? What is the advantage of this behavior as still if we wants to use that reference variable we get NullPointerException?
ASKER CERTIFIED SOLUTION
Avatar of sciuriware
sciuriware

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
SOLUTION
Avatar of Mick Barry
Mick Barry
Flag of Australia image

Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of sciuriware
sciuriware

In fact this is a very old problem (back in the 1950's):
how could the compiler predict that, somehow, a variable will get a proper value in the long run?

All a compiler can do is warn you that code might be missing.

A good reason to start to use an IDE like ECLIPSE: it is smarter and warns you that
a variable SOMETIMES (conditional) will not have a proper value.

;JOOP!
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Avatar of gksinghiet

ASKER

>>Because all local vars *must* be explicitly initialized before being used...
Yes this constraint is enforced by java compiler but I want to know the advantage of enforcing this.
>>how could the compiler predict that, somehow, a variable will get a proper value in the long run
Just by checking its reference value where the variable is used. Like one did in his code as: if (ref == null){}
>>Actually this is done to promote good programming practice
Yes you are right that declaring local variable immediately before using mitigates the chances of error but my question is that by allowing a reference variable to be declaring with null value what are we achieving?
>>Just by checking its reference value where the variable is used. Like one did in his code as: if (ref == null){}
Sorry it is not that easy, as at runtime the value might change. But still it dosn't answers my question because then the compiler should allow the reference variable to be used with being initialized instead of initializing it with null.
>>>  the compiler should allow the reference variable to be used with being initialized instead of initializing it with null.
That's the point! How would you check if a reference is valid if you could not compare it to null?

;JOOP!
>>That's the point! How would you check if a reference is valid if you could not compare it to null?
But at the time of initialization compiler can check for the null reference. Isn't it?
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
In Java, Class and Instance variables need not be explicitly initialized with anything... The compiler automatically assigns an initial value.
I guess the point of ur contention is y Local variables are treated differently and since the compiler already goes to the trouble of assigning initial values for non-local variable, y not just go ahead and provide initial values to local-variables.. right ??

well.. my take on the whole thing is that class and instance variables are required to maintain the state of an object, its is expected to keep changing over the life time of the program and therefore has a scope = lifetime of the object, Thus initial values are not really important, its just the value at any point of time thats significant..

on the other hand, Local variables are to be used within methods and are not supposed to be used to record state, its supposed to be used as temporary objects. The JVM architecture states that Java initializes something called a "Method area". Althought this method area is created on the heap, the initial size is probably calculated and optimized based on how local variables are initialized..

-KuTtZ
check out the VM specs

http://java.sun.com/docs/books/vmspec/2nd-edition/html/Overview.doc.html

espescially section 3.5 and 3.6.
Apparantly Local Variables ARE allocated on a Stack (which can be made expandable). which could be the reason y u have to explicitly initialize Local Variables...

-KuTtZ
>> Class and Instance variables need not be explicitly initialized with anything... The compiler automatically assigns an initial value.

Yes, but if you use it without initializing, it is likely to give an error. Like:

String a ;
String b = a.trim () ; // will give a compilation error that 'a' might not have been initialized
However, if it is used somewhere else, it might not give an error but might just throw an exception upon usage. Like:

public class Test
{
  private String a ;
  public String getA ()
  {
    return a ; // no compilation error here
  }
}

Test obj = new Test () ;
String c = obj.getA ().trim () ; // will throw NullPointerException
> String a ;
> String b = a.trim () ; // will give a compilation error that 'a' might not have been initialized

will definitely NOT give a compilation error... it will only throw a Runtime NullPointerException.
as the compiler DOES initialize it to null..

-KuTtZ
i mean.. if String a is an Instance/Class cariable... that is

-KuTtZ
>> will definitely NOT give a compilation error... it will only throw a Runtime NullPointerException

It WILL give a compile time error if it is local to a method.
>> if String a is an Instance/Class cariable... that is
>> as the compiler DOES initialize it to null..

Yes, in that case it will throw an exception because you are defining it somewhere else and using it somewhere else, like in http:#16604514
Well what's the use of this discussion sofar?
Did we learn something?

;JOOP!
From the earlier comments, the asker still did not had it clear: >> But at the time of initialization compiler can check for the null reference. Isn't it?

Hopefully some more explanation will help him understand in which cases it will throw an exception and in which cases it will generate a compile-time error.
>> check out the VM specs
I will go through the spec and then come back to the discussion.
Actually I know when the compiler complains and when it will not.
But I have a curiosity that why the language implementers have putted in such constraint.
>> But I have a curiosity that why the language implementers have putted in such constraint.

It is good. Whenever it can warn you of potential errors, it does. Because it knows that if you use an uninitialized variable by calling a method on it, it will throw an Exception. So wherever possible, it tries to save you from doing that. I only see something positive there. What negative do you see? You don't want your code to thrown an exception.
>> I only see something positive there.
I couldn't see any thing positive or negative.
Take for example that if JVM allows a local refernce variable to be used without initializing it then it will set it with a default value null as in case of instance or class variables. And ultimately by allowing a local reference variable to be initialize with null it is still doing the same.
>> And ultimately by allowing a local reference variable to be initialize with null it is still doing the same.

No, you need not initialize it with a nul alwaysl. You can initialize it with something else. For example, in:

String a = "Hello" ;
int i = a.length () ;

At least by forcing you to explicitly initialize it with something, it is making sure tha you are aware of what value you are using to initialize it and therefore if any exception still happens after that, it is forced by your value (e.g., if you still initialize it to null and call length () on it, it is helpless - it has to throw). But it makes sure *you did not forget to initialize it by mistake*, in case you intended to initialize it with something relevant (not necessarily null).
In some exception-handling scenarios also, it is helpful (when resources have to be released in finally blocks):

FileInputStream fis = null ; // initialize, to avoid compile-time error in finally block
try
{
  fis = new FileInputStream ( .... ) ;
  // read data from the file
}
catch ( Exception e )
{
  e.printStackTrace () ;
}
finally
{
  if ( fis != null ) // if we had not initialized it outside the try block, this would give an error
    fis.close () ;
}

In this kind of a case, initializing it to null is sufficient because later we are making sure we call methods on it only if it has a non-null value so there will not be run-time exceptions. The null initialization is to get rid of the compile-time error because we choose to close it in the finally block and not the try block as a good programming practice (since finally will be executed even if there is some I/O exception in the try block, in between). If we had wanted to close it in the try block itself as a bad programming practice, we wouldn't have needed to initialize it to null outside, because inside the try block it is anyway initialized to a new object.
gksinghiet, by now you know how it works.
If you really want to know why, contact the SUN people:
you will be surprised, embarrased and you will still not understand why.
Many of us tried that once.

Try to use it. It's a fact of (JAVA) life now.

;JOOP!
SOLUTION
Link to home
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
Start Free Trial
Last paragraph I mean to type, "developers /don't/ typically try to reduce method invocation." :-(
I found myself confused in deciding whom to give points and whom not to give, as all inputs are valued for me.
So I leave this responsibility to Administrator.
But I definitely like to thanks all experts for there valued inputs. Thanks a lot :-)