2013-06-12 9 views
6

Chcę trochę dyskusji na ten temat, ale nie mogłem wywnioskować odpowiedzi na moją sprawę. Nadal potrzebujesz pomocy.Java: nie można uzyskać dostępu do chronionego członka nadklasy w rozszerzającej podklasie

Oto mój kod:

package JustRandomPackage; 

public class YetAnotherClass{ 
    protected int variable = 5; 
} 
package FirstChapter; 

import JustRandomPackage.*; 

public class ATypeNameProgram extends YetAnotherClass{ 
    public static void main(String[] args) { 

     YetAnotherClass bill = new YetAnotherClass(); 
     System.out.println(bill.variable); // error: YetAnotherClass.variable is not visible 

    } 
} 

Niektóre definicje, po której, w przykładzie powyżej wydaje się być mylące:

1. Subclass is a class that extends another class. 
2. Class members declared as protected can be accessed from 
    the classes in the same package as well as classes in other packages 
    that are subclasses of the declaring class. 

Pytanie: Dlaczego nie mogę Mam dostęp do chronionego elementu (int variable = 5) z instancji podklasy YetAnotherClass (bill obiekt)?

+1

Co to jest pytanie? –

Odpowiedz

3

Klasy w innych pakietach, które są podklasami klasy deklarującej, mogą uzyskiwać dostęp tylko do swoich własnych dziedziczonych członków protected.

public class ATypeNameProgram extends YetAnotherClass{ 
    public ATypeNameProgram() { 
     System.out.println(this.variable); // this.variable is visible 
    } 
} 

... ale nie inne obiekty dziedziczone protected członków.

public class ATypeNameProgram extends YetAnotherClass{ 
    public ATypeNameProgram() { 
     System.out.println(this.variable); // this.variable is visible 
    } 

    public boolean equals(ATypeNameProgram other) { 
     return this.variable == other.variable; // error: YetAnotherClass.variable is not visible 
    } 
} 
+0

To jest złe. Ten kod się kompiluje. Klasa w innym pakiecie może uzyskać dostęp tylko do odziedziczonych chronionych elementów, które są tego samego typu co sama klasa. –

1

rachunek nie należy do podklasy YetAnotherClass. rachunek jest oddzielną YetAnotherClass.

Wypróbuj int bill = this.variable; (wewnątrz konstruktora), aby uzyskać dostęp do członków podklasy.

0

Nie tworzysz instancji klasy, która je rozszerza, ale klasy nadrzędnej. Sprawdź kod poniżej:

public class ATypeNameProgram extends YetAnotherClass{ 
    public static void main(String[] args) { 

     YetAnotherClass bill = new YetAnotherClass(); 
     System.out.println(bill.variable); // error: YetAnotherClass.variable is not visible 

     ATypeNameProgram a = new ATypeNameProgram(); 
     System.out.println(a.variable); //this will work 

    } 
} 
1

Twój kod będzie działać, jeśli YetAnotherClass będzie w tym samym opakowaniu jako ATypeNameProgram. Jak napisali inni, nie będzie działać w innych przypadkach. Oto działający przykład.

package my.example; 

public class MainClass extends MyAnotherClass { 
    public static void main(String[] args) { 
     MyAnotherClass bill = new MyAnotherClass(); 
     System.out.println(bill.value); // this will work 
    } 
} 

package my.example; 

public class MyAnotherClass { 

    protected int value = 5; 

} 
1

Klasa Foo mają dostęp tylko do chronionych członków instancja typu Bar wtedy i tylko wtedy Bar jest przypisane do Foo. To znaczy, jeśli możemy napisać:

Foo foo = new Bar(); 

Załóżmy, że mamy:

package a; 

public class Base { 
    protected int protectedField; 
} 

Wtedy możemy mieć to:

package b; 

import a.Base; 

public class Parent extends Base { 
    void foo() { 
     int i = this.protectedField; 
    } 
    void foo(Parent p) { 
     int i = p.protectedField; 
    } 
    void foo(Child c) { 
     int i = c.protectedField; 
    } 
} 

class Child extends Parent { } 

będzie to skompilować, ponieważ wszystkie protectedField s są dostępne za pośrednictwem instancji Parent. Zauważ, że ponieważ odwołanie Parent może być instancją Child (tzn. Możemy napisać Parent p = new Child();), możemy uzyskać dostęp do c.protectedField.

Poniżej przedstawione są nie opracowanie:

package b; 

import a.Base; 

public class Parent extends Base { 
    void foo(Stepchild sc) { 
     int i = sc.protectedField; // ERROR 
    } 
} 

class Stepchild extends Base {} 

ponieważ wystąpienie Stepchild nie jest przykładem Parent.

Nieco mylący, nie będzie to skompilować albo:

package b; 

import a.Base; 

public class Parent extends Base {} 

class Child extends Parent { 
    void foo(Parent p) { 
     p.protectedField; // ERROR 
    } 
} 

to dlatego, że obiekt nie jest Parent nadklasą lub superinterface z Child, a więc Child nie może uzyskać dostępu do jego chronionych członków.

Jeśli kiedykolwiek będziesz miał problemy z pamięcią, zastanów się, czy typ może zostać zapisany w referencji do rodzaju klasy. Na przykład, możemy napisać:

Parent p = new Child(); 

ale nie można napisać

Child c = new Parent();  // ERROR 
Parent p = new Stepchild(); // ERROR 

Child więc nie będzie miał dostępu do Parent „s chronionych członków, a Parent nie będą mieli dostępu do Stepchild” s członków chronione .

Parę końcowe punkty:

Pamiętaj, że protected dostępu umożliwia widoczność wśród opakowaniu. Z mojego doświadczenia wynika, że ​​ludzie o tym zapominają.

Wreszcie, członkowie protected static są zawsze widoczni w hierarchii dziedziczenia.

Powiązane problemy