Protected member behavior once it was inherited.
Asked Answered
D

4

6

I've got some doubts regarding protected identifier. In the first chapter of Sun Certified Java Programmer Study Guide by K.Sierra I found the following information:

"Once the subclass-outside-the-package inherits the protected member, that member (as inherited by the subclass) becomes private to any code outside the subclass, with the exception of subclasses of the subclass."

I provided sample code which reflects the above statement and it is absolutely clear to me.

// Parent class
package package1;

import package2.Child;
public class Parent {

    protected int i = 5;

}

// Child class
package package2;

import package1.Parent;

public class Child extends Parent {

    // variable 'i' inherited

}


package package2;

public class Neighbour {

    public void protectedTesting(){
        Child child = new Child();
        System.out.println(child.i); // no access
    }
}

I've started experimenting and made a small change - moved Neighbour to package1. And there is an access to "i" variable which is a little bit surprising for me as it is not in accordance to statement "becomes private to any code outside the subclass"

Neighbour class after change:

package package1;

import package2.Child;

public class Neighbour {

    public void protectedTesting(){
        Child child = new Child();
        System.out.println(child.i); // access!
    }
}

Please clarify it to me. Thanks.

Dratted answered 12/10, 2012 at 14:58 Comment(0)
A
5

In short, protected is package-private as well as visible to subclasses. Even the JLS is vague on this (JLS §6.6.2):

A protected member or constructor of an object may be accessed from outside the package in which it is declared only by code that is responsible for the implementation of that object.

It specifies that outside the package, only subclasses can access protected members. This implies that you can also access the variable within the package. It's poor wording, but true nonetheless that protected members have package-level visibility as well as subclass-level visibility.

See also:

Areta answered 12/10, 2012 at 15:7 Comment(0)
C
3

And there is an access to "i" variable which is a little bit surprising for me as it is not in accordance to statement "becomes private to any code outside the subclass"

--> But you moved class Neighbour in package package1 which is true according to "Protected members can be accessed by classes in same package"

"Once the subclass-outside-the-package inherits the protected member, that member (as inherited by the subclass) becomes private to any code outside the subclass, with the exception of subclasses of the subclass."

--> Inside package it is still protected and not private for all classes within the package.

Consideration answered 12/10, 2012 at 15:7 Comment(1)
+1 - for explaining why the behaviour observed by the OP is actually consistent with K.Sierra's book.Antemundane
O
1

The truth is not in "Sun Certified Java Programmer Study Guide" but in the Java Language Specification

6.6.2. Details on protected Access

A protected member or constructor of an object may be accessed from outside the package in which it is declared only by code that is responsible for the implementation of that object.

Overbearing answered 12/10, 2012 at 15:5 Comment(2)
It is true that the SCJPSG is not definitive. However, that doesn't make it incorrect. See Nandkumar Tekale's answer.Antemundane
"Once the subclass-outside-the-package inherits the protected member, that member (as inherited by the subclass) becomes private TO ANY CODE outside the subclass" - Personally, I find it incorrect and misleading.Dratted
M
1

protected visibility includes package level visibility. Inheritance allows you to treat your Child object as an instance of Parent. As the member i of Parent is declared in the same package, it is accessible from Neighbour.

package package1;

import package2.Child;

public class Neighbour {

    public void protectedTesting() {
        Parent neighboured = new Child();
        System.out.println(neighboured.i); // access
    }
}
Muskellunge answered 12/10, 2012 at 15:33 Comment(0)

© 2022 - 2024 — McMap. All rights reserved.