Middle
Jakie rodzaje klas zagnieżdżonych istnieją?
sobes.tech AI
Odpowiedź od AI
Zagnieżdżone klasy (Nested Classes) w Javie dzielą się na dwa główne typy:
-
Statyczne klasy zagnieżdżone (Static Nested Classes)
- Oznaczone modyfikatorem
static. - Zachowują się jak zwykłe statyczne członkowie klasy kontenera.
- Mogą uzyskać dostęp do statycznych członków klasy zewnętrznej (nawet jeśli są prywatne).
- Nie mają bezpośredniego dostępu do nie-statycznych członków klasy zewnętrznej.
- Tworzone bez instancji klasy zewnętrznej:
OuterClass.StaticNestedClass nestedObject = new OuterClass.StaticNestedClass();.
- Oznaczone modyfikatorem
-
Klasy wewnętrzne (Inner Classes)
Klasy wewnętrzne nie są oznaczone
statici są powiązane z instancją klasy zewnętrznej. Dzielą się na:-
Klasy członkowskie (Member Inner Classes)
- Deklarowane na poziomie członka klasy kontenera, ale poza jej metodami.
- Mają dostęp do wszystkich członków klasy zewnętrznej, w tym prywatnych.
- Wymagają instancji klasy zewnętrznej do utworzenia własnej instancji:
OuterClass outerObject = new OuterClass(); OuterClass.MemberInnerClass innerObject = outerObject.new MemberInnerClass();.
-
Klasy lokalne (Local Classes)
- Tworzone wewnątrz metod, konstruktorów lub bloków inicjalizacyjnych.
- Zakres ich widoczności jest ograniczony do bloku, w którym są zadeklarowane.
- Nie można ich deklarować z modyfikatorami dostępu (
public,private,protected). - Mogą odwoływać się do lokalnych zmiennych finalnych lub efektywnie finalnych z zewnętrznego bloku.
- Nie mogą być używane poza blokiem, w którym są zdefiniowane.
-
Klasy anonimowe (Anonymous Classes)
- W istocie są to anonimowe klasy lokalne.
- Deklaruje się je i instancjonuje jednocześnie.
- Używa się ich do implementacji klasy abstrakcyjnej lub interfejsu "na żywo".
- Podobnie jak klasy lokalne, mają dostęp do lokalnych zmiennych finalnych lub efektywnie finalnych z zewnętrznego bloku.
-
Przykład struktury:
class OuterClass {
private int outerField;
private static int staticOuterField;
// Statyczna klasa zagnieżdżona
static class StaticNestedClass {
void accessOuter() {
// Może odwołać się do statycznych członków klasy zewnętrznej
int value = staticOuterField;
// Nie może odwołać się do nie-statycznych członków
// int value2 = outerField; // Błąd kompilacji
}
}
// Klasa członkowska (klasa wewnętrzna)
class MemberInnerClass {
void accessOuter() {
// Może odwołać się do wszystkich członków klasy zewnętrznej
int value1 = outerField;
int value2 = staticOuterField;
}
}
void methodWithLocalAndAnonymous() {
final int localVar = 10; // final lub efektywnie final
// Klasa lokalna
class LocalClass {
void accessOuter() {
// Może odwołać się do członków klasy zewnętrznej i lokalnych finalnych/efektywnie finalnych zmiennych
int value1 = outerField;
int value2 = staticOuterField;
int localValue = localVar;
}
}
LocalClass localObj = new LocalClass();
localObj.accessOuter();
// Klasa anonimowa (implementująca Runnable)
Runnable anonymousRunnable = new Runnable() {
@Override
public void run() {
// Może odwołać się do członków klasy zewnętrznej i lokalnych finalnych/efektywnie finalnych zmiennych
int value1 = outerField;
int value2 = staticOuterField;
int localValue = localVar;
System.out.println("Uruchomione z lokalną zmienną: " + localValue);
}
};
anonymousRunnable.run();
}
}