Cannot access an Object Reference instantiated by

2019-09-24 10:05发布

问题:

I have an abstract class that declares a number of object references, specifically a JLabel. I have two classes that both extend that class. One of the children instantiates the JLabel and calls a couple of its methods. That classes sibling attempts to call the setText method on the JLabel and I get a NullPointerException(The sibling that instantiates it is called before the other.)

I had thought that all children refer to the same object in memory and would thus modify the same object but apparently I'm wrong. How can I get around this?

Here is an example of what I mean:

public class BlahDriver 
{
    public static void main(String[] args) 
    {
        BlahChildOne blah = new BlahChildOne();
        BlahChildTwo blah2 = new BlahChildTwo();
    }
}
public abstract class Blah 
{
    protected JLabel label;
}
public class BlahChildOne extends Blah
{
    public BlahChildOne()
    {
        label = new JLabel();
    }
}
public class BlahChildTwo extends Blah
{
    public BlahChildTwo()
    {
        label.setText("Fred");
    }
}

I get a NullPointerException at BlahChildTwo when attempting to setText.

回答1:

So, blah defines an instance field called label but does not initialise it

public abstract class Blah 
{
    protected JLabel label;
}

BlahChildOne initialises the label from Blah

public class BlahChildOne extends Blah
{
    public BlahChildOne()
    {
        label = new JLabel();
    }
}

BlahChildTwo does not initialises the label from Blah, so it is still null...

public class BlahChildTwo extends Blah
{
    public BlahChildTwo()
    {
        label.setText("Fred");
    }
}

Neither BlahChildOne or BlahChildTwo share information between them (they have commonality through inheritance from Blah, but the actually information is each owns).

Think of it like identical twins, they might share commonality, but just because one get's sick, doesn't mean the other will, they are their own self contained instance.

IF you want to share information between classes, you should consider providing a reference to the class with the information you want to share, for example...

public class BlahChildTwo extends Blah
{
    public BlahChildTwo(Blah blah)
    {
        label = blah.label;
        label.setText("Fred");
    }
}

But I'd really like to see a use case for something so drastic...

Why static is consider bad

Lets assume...

public abstract class Blah 
{
    protected static JLabel label;
}

Now in your code, you do something like...

BlahChildOne bco = new BlahChildOne();
add(bco.label); // It the label to the screen...
BlahChildTwo bct = new BlahChildTwo();

Okay, so far, so good. Now imagine, somewhere else in your code, you do...

BlahChildOne bco = new BlahChildOne();
BlahChildTwo bct = new BlahChildTwo();

...But why hasn't the screen updated? Because Blah#label is no longer pointing to the JLabel which you previously added to the screen, you've lost that reference.

This is pain in the debugger to find, even when you know what you are looking for, because there is no accountability, any class that extends Blah can create a new instance of JLabel and assign it to label.



回答2:

Friend, you must be new to object oriented programming.

A class is a template for objects. When you instantiate a class (i.e. new Child()), memory is allocated on the heap to store that object's instance variables. That memory, containing the object's variables, is for that one object alone. Each time you create an object, it has its own instance variables in a separate memory space.



回答3:

This line protected JLabel label; doesn't creates Object , It is only reference variable , So when both class extends Abstract class . Both Class have their own seperate copies of Reference Variable

BlahChildTwo has his own copy of JLabel reference variable which is not instantiated that is why you are facing NullPointerException

Now coming to your question

I had thought that all children refer to the same object in memory and would thus modify the same object but apparently I'm wrong. How can I get around this?

Yes all children will refer to same object if that is an object Not Reference Variable



回答4:

All children do not refer to the same object. Each child object will be a new object that will have its own copy of all references declared in the parent as well as a copy of all references declared in itself.

If you want to access the same reference between classes, try making it static in the parent class.