4

Why is it that when I create a reference of the super class in the sub-classs that only methods that are public can be called from the reference and not methods that are protected. (The classes are in different packages)

package pet;

public class Dog {
    protected void bark(){};
    void jump(){};  
    public void lick(){};
}


package other;
import pet.*;

public class Husky extends Dog {
    public static void main(String[] args){ 
        Husky h = new Husky();
        h.bark();     //COMPILES (Husky is a subclass of Dog - Protected method)
        h.jump();     //DOES NOT COMPILE (Different packages - package-private access method)

        Dog d = new Dog();
        d.bark();   //DOES NOT COMPILE WHY?
        d.jump();   //DOES NOT COMPILE (Different packages - package-private access method)
        d.lick();   //COMPILES (Method is public)
    }
}

My question is why doesn't d.bark() compile? The bark method has an access modifier of protected, which allows it to be accessed from classes in the same package or subclasses. So what's going on?

If the husky reference is able to access the bark method, by the same logic the dog reference should also be able to access the bark method.

So I can only assume that there must be an issue with the Dog reference?

RamanSB
  • 1,162
  • 9
  • 26
  • good question. we know the access rules of `protected` (see my [summary](http://stackoverflow.com/a/32263340/2158288) ), but we need to find the justifications as well. – ZhongYu Sep 16 '15 at 18:36
  • @bayou.io Thanks for the link to your summary: "The access obj.m is granted only if B is subclass of A, and C is subclass of B or C is B" What if C is A? Why won't that work? – RamanSB Sep 16 '15 at 18:41
  • @wero I just read the answer from that link... What I'm about to ask may seem quite stupid... If public and protected members are both visible, why is it that we can access the public fields but not protected? – RamanSB Sep 16 '15 at 18:52
  • well, this is not a trivial question. allow me some time to think about it. – ZhongYu Sep 16 '15 at 19:26
  • @bayou.io what are your views on the answers presented below? – RamanSB Sep 16 '15 at 21:02
  • @SotiriosDelimanolis I have checked the duplicate post you have suggested the answer that was verified stated: "You can access the protected members declared in A from within C, but only for instances of C or subclasses of C." Why is this the case? – RamanSB Sep 16 '15 at 21:05
  • That's how `protected` is defined. You need to own the implementation. You're writing `C`, you own that, so you have access to its view of the `protected` member(s). You don't own `A`, so you don't have access to them, through an `A` reference. – Sotirios Delimanolis Sep 16 '15 at 21:07
  • @SotiriosDelimanolis When you say I am writing C? In this case Husky class is C? Is there a way we can continue this conversation in a chat room? – RamanSB Sep 16 '15 at 21:08
  • http://chat.stackoverflow.com/rooms/89859/protected-modifier – Sotirios Delimanolis Sep 16 '15 at 21:10

1 Answers1

0

Though access modifiers plays an important role in inheritance but this problem should not be confused with inheritance. As @vikss rightly said that Super class is not aware of the inheritance tree below thus i does not know whether Huskey can access its protected members. To your question :

Dog d = new Dog();
    d.bark(); 

At run time the methods are resolved by the underlying object which which is being referred . Here the underlying object is of Dog superclass and that too we are accessing it with Dog reference it self. This narrows down the problem of accessing protected members out of the package which is not allowed.

And also your code d.bark(); lies in main method which itself is a seperate entity from Huskey's Object. One more interesting fact you can not even call Dog d = new Dog(); d.bark(); from a another member method of Huskey's class(here comes access modifiers), but you can very well call bark() method directly in the same member method (here comes inheritance).

Hope it helps!

Jor El
  • 199
  • 9