В чем разница между модификаторами доступа package-private (default) и protected в Java?

«В чем разница между модификаторами доступа package-private (default) и protected в Java?» — вопрос из категории Java Core, который задают на 10% собеседований Java Разработчик. Ниже — развёрнутый ответ с разбором ключевых моментов.

Ответ

Package-private (default) — модификатор доступа по умолчанию, применяемый, когда модификатор не указан явно. Он разрешает доступ к члену класса только для классов из того же пакета.

Protected — разрешает доступ:

  1. Классам из того же пакета (как package-private).
  2. Подклассам (наследникам), даже если они находятся в других пакетах.

Пример, иллюстрирующий разницу:

// Файл: com/example/Parent.java
package com.example;

public class Parent {
    void packagePrivateMethod() {} // Доступ только в пакете com.example
    protected void protectedMethod() {} // Доступ в пакете com.example + подклассы
}
// Файл: com/other/Child.java
package com.other;
import com.example.Parent;

public class Child extends Parent {
    void test() {
        // packagePrivateMethod(); // ОШИБКА КОМПИЛЯЦИИ: класс в другом пакете
        protectedMethod(); // OK: Child является подклассом Parent
    }
}

Итог: protected расширяет видимость package-private, добавляя доступ для подклассов вне пакета.