1. The Hook (The "Byte-Sized" Intro)
- In a Nutshell: Access modifiers control the visibility of classes, methods, and variables.
- Java has four levels: private (class only), default/package-private (package only), protected (package + subclasses), and public (everywhere). They're the foundation of encapsulation and API design.
Think of building security clearances:
- Private: CEO office (only CEO)
- Package-private: Company floor (employees only)
- Protected: Company + branches (employees + partners)
- Public: Lobby (anyone can enter)
2. Conceptual Clarity (The "Simple" Tier)
💡 The Analogy: The Document Classification
Government documents:
- Top Secret (private): Need-to-know only
- Internal (default): Department access
- Confidential (protected): Agency + approved partners
- Declassified (public): Public domain
Hand-Drawn Logic Map
graph TD
A[Access Modifiers] --> B[private]
A --> C[default]
A --> D[protected]
A --> E[public]
B --> B1[Same class ONLY]
C --> C1[Same package]
D --> D1[Same package + Subclasses]
E --> E1[Everywhere]
style B fill:#D32F2F
style C fill:#F57C00
style D fill:#2E7D32
style E fill:#2E7D32
3. Technical Mastery (The "Deep Dive")
Access Levels Table
| Modifier | Same Class | Same Package | Subclass (Other Package) | Other Packages |
|---|---|---|---|---|
| private | ✅ | ❌ | ❌ | ❌ |
| default | ✅ | ✅ | ❌ | ❌ |
| protected | ✅ | ✅ | ✅ | ❌ |
| public | ✅ | ✅ | ✅ | ✅ |
The "Why" Paragraph
Why multiple levels? Principle of Least Privilege—expose only what's necessary. Make fields private to hide implementation. Use public for APIs. protected for extension points. default for package-internal utilities. This prevents misuse, allows internal changes without breaking users, and creates clear contracts.
4. Interactive & Applied Code
java
// File: com/example/Parent.java
package com.example;
public class Parent {
private int privateField = 1; // Only within Parent
int defaultField = 2; // Same package
protected int protectedField = 3; // Package + subclasses
public int publicField = 4; // Everywhere
private void privateMethod() { }
void defaultMethod() { }
protected void protectedMethod() { }
public void publicMethod() { }
}
// File: com/example/SamePackage.java
package com.example;
public class SamePackage {
void test() {
Parent p = new Parent();
// p.privateField; // ❌ ERROR
int a = p.defaultField; // ✅ OK (same package)
int b = p.protectedField; // ✅ OK (same package)
int c = p.publicField; // ✅ OK
}
}
// File: com/other/Child.java
package com.other;
import com.example.Parent;
public class Child extends Parent {
void test() {
// privateField; // ❌ ERROR
// defaultField; // ❌ ERROR (different package)
int a = protectedField; // ✅ OK (subclass)
int b = publicField; // ✅ OK
}
}
// File: com/other/Unrelated.java
package com.other;
import com.example.Parent;
public class Unrelated {
void test() {
Parent p = new Parent();
// p.privateField; // ❌ ERROR
// p.defaultField; // ❌ ERROR
// p.protectedField; // ❌ ERROR (not a subclass reference)
int a = p.publicField; // ✅ OK
}
}5. The Comparison & Decision Layer
Decision Tree: Which Modifier?
graph TD
A{Should ANYONE access it?}
A -- No --> B[private]
A -- Yes --> C{Only within package?}
C -- Yes --> D[default]
C -- No --> E{Subclasses should access?}
E -- Yes --> F[protected]
E -- No --> G[public]
6. The "Interview Corner" (The Edge)
The "Killer" Interview Question: "What's the difference between default and protected?" Answer:
- Default: Accessible within the same package only (no subclass privilege)
- Protected: Accessible within the same package AND by subclasses in any package
Key: Protected gives subclasses access even across packages!
Pro-Tip: Start restrictive, widen later:
java
private int count; // Start private
// If needed later, make it protected or public
// Going restrictive (public → private) breaks clients!Rule: Make everything private by default. Only make it more visible if needed!