Thilo dodał dobrą odpowiedź na Twoje pierwsze pytanie „Jak to możliwe?”. Chciałbym nieco rozwinąć drugie zadane pytanie: Dlaczego takie zachowanie jest dozwolone?
Na początek wyjaśnijmy, że to zachowanie nie ogranicza się do klas wewnętrznych, które z definicji są niestatycznymi typami zagnieżdżonymi. To zachowanie jest dozwolone dla wszystkich typów zagnieżdżonych, w tym zagnieżdżonych wyliczeń i interfejsów, które muszą być statyczne i nie mogą mieć obejmującego wystąpienia. Zasadniczo model jest uproszczeniem do następującej instrukcji: Zagnieżdżony kod ma pełny dostęp do otaczającego kodu - i odwrotnie.
Więc dlaczego? Myślę, że przykład lepiej to ilustruje.
Pomyśl o swoim ciele i mózgu. Jeśli wstrzykniesz heroinę w ramię, twój mózg się rozpali. Jeśli obszar ciała migdałowatego twojego mózgu zobaczy, co według niego stanowi zagrożenie dla twojego osobistego bezpieczeństwa, na przykład osa, sprawi, że twoje ciało obróci się w drugą stronę i pobiegnie w kierunku wzgórz bez Ciebie „zastanawiasz się” dwa razy o tym.
Mózg jest więc nieodłączną częścią ciała - i, co dziwne, także na odwrót. Korzystanie z kontroli dostępu między tak blisko powiązanymi podmiotami powoduje utratę praw do związku. Jeśli potrzebujesz kontroli dostępu, musisz bardziej rozdzielić klasy na naprawdę odrębne jednostki. Do tego czasu są tą samą jednostką. Dobrym przykładem dla dalszych badań byłoby przyjrzenie się, jak Iterator
zwykle implementowana jest Java .
Nieograniczony dostęp od kodu zamykającego do kodu zagnieżdżonego sprawia, że w większości przypadków dodawanie modyfikatorów dostępu do pól i metod typu zagnieżdżonego jest raczej bezużyteczne. Takie postępowanie dodaje bałaganu i może zapewnić fałszywe poczucie bezpieczeństwa dla nowych użytkowników języka programowania Java.