4
public class Program {

    public static void main(String[] args) {
        Listener listener = new Listener();
        listener.listen();
    }
}

public class Listener {

    ServerQuery query;
    int test = 1;

    public listen() {
        query = new ServerQuery();
        Channel ch = new Channel();
        ch.dupa();
    }
}

public class Channel extends Listener {

    public dupa() {
        System.out.print(test); // works fine 
        super.query.doSomething(); // null pointer
        query.doSomething(); //  null pointer
    }
}

I cant access variable "query" in class "Channel". Can anyone explain me why ?

BobTheBuilder
  • 17,650
  • 5
  • 35
  • 58
user1652792
  • 309
  • 3
  • 15

5 Answers5

3

You misunderstood the concept of super type and sub type.

the direct problem is that you need to instantiate query variable before using it.

Either call ch.listen() before you call dupa or call it inside dupa.

The main issue here is understanding subtype-supertype relation.

Your Channel object doesn't have a reference to an instance of Listener , its just a subtype of it. So if you need to access a field of your supertype, like accessing a field of your class - you must instantiate it before you use it.

There's no logic in creating Channel object inside Listener. Channel is a Listener, so you can create it instead.

I suggest you read more about it here or anywhere else.

For you code, you can use:

public class Program {

    public static void main(String[] args) {
        Channel ch = new Channel();
        ch.listen(); // will instantiate ch.query
        ch.dupa(); 
    }
}
public class Listener {

    ServerQuery query;
    int test = 1;

    public listen() {
        query = new ServerQuery();
    }
}

public class Channel extends Listener {

    public dupa() {
        System.out.print(test);
        super.query.doSomething();
        query.doSomething();
    }
}
BobTheBuilder
  • 17,650
  • 5
  • 35
  • 58
1

Edited for more explanation:

Variables in the superclass have to be defined as protected to allow being implemented by subclasses. If you don't declare a scope, the field is declared as package-private.

More info on scopes can be found in the official tutorial.

Another remark on your code: your query variable isn't instantiated here, so it will always return a NPE if you don't call the method listen() first.

Jeroen Vannevel
  • 41,258
  • 21
  • 92
  • 157
0

I solved it by making something like that:

public class Channel extends Listener {
     ServerQuery queryInstance;
     Listener(ServerQuery listener){
         queryInstance = listener;
     }
     public dupa() {

        System.out.print(test); // works fine 
        super.query.doSomething(); // null pointer
        query.doSomething(); //  null pointer
    }
}
user1652792
  • 309
  • 3
  • 15
0

Channel ch = new Channel(); does not initialize query.

You are calling dupa() on the Channel object without calling listen() which initializes the query reference.

0

You are working with two Listener objects. One that is in Channel class (say Channel.super()) and one that is in your main method.

I think the confusion is that you are assuming that your Channel object will make use of the same listener class that you declared in your main method.

In a nutshell, the answer is that query variable is not initialized.

So mainly you have a design issue. You can fix it couple of ways. One simple one would be to pass in the query to your dupa method and the make use of that query object.

Nilesh Tailor
  • 148
  • 2
  • 6