Understanding Access Modifiers in Java

When it comes to writing clean and maintainable Java code, one of the essential aspects to consider is controlling the visibility of your class members. Access modifiers in Java are keywords used to define the visibility or accessibility of classes, methods, variables, or other members within a Java program. They help control the level of encapsulation and access to class members, ensuring proper data hiding and security in your code. Java has four main access modifiers:

Public Access Modifier

The public access modifier is the most permissive one. When you declare a class, variable, or method as public, it becomes accessible from anywhere within your codebase, both within and outside the class, package, or project. This is the widest scope of accessibility.

				
					public class PublicAccessClass {
    public int publicVar;
    
    public void publicMethod() {
        // Code here
    }
}

				
			

In the example above, the publicVar and publicMethod can be accessed from any part of your code, making them publically available to other classes and packages.

Protected Access Modifier

The protected access modifier restricts access to class members but allows subclasses to access them. A protected member is accessible within the same class, in subclasses (even if they are in different packages), and within the same package. However, outside the package, protected members are not accessible.

				
					public class ProtectedAccessClass {
    protected int protectedVar;
    
    protected void protectedMethod() {
        // Code here
    }
}

				
			

In this example, protectedVar and protectedMethod can be accessed from subclasses, ensuring that they are available for extension and customization.

Private Access Modifier

The private access modifier is the most restrictive. Members marked as private are only accessible within the same class. They are not visible to subclasses or other classes, even if they are in the same package.

				
					public class PrivateAccessClass {
    private int privateVar;
    
    private void privateMethod() {
        // Code here
    }
}

				
			

In this case, privateVar and privateMethod are entirely hidden from other classes, ensuring the highest level of encapsulation and data hiding.

Default (Package-Private) Access Modifier

When you don’t specify an access modifier, the default access modifier is applied. Members with default access are only accessible within the same package. They are not visible outside the package.

				
					class DefaultAccessClass {
    int defaultVar;
    
    void defaultMethod() {
        // Code here
    }
}

				
			

Here, defaultVar and defaultMethod are accessible only within the package where DefaultAccessClass is defined. They are not visible to classes outside this package.

Let’s see how these access modifiers work in practice:

				
					// In ClassA.java
public class ClassA {
    public int publicVar;
    protected int protectedVar;
    int defaultVar;
    private int privateVar;

    public void publicMethod() {
        // Code here
    }

    protected void protectedMethod() {
        // Code here
    }

    void defaultMethod() {
        // Code here
    }

    private void privateMethod() {
        // Code here
    }
}

// In ClassB.java (in the same package)
public class ClassB {
    public void accessExample() {
        ClassA myObj = new ClassA();
        myObj.publicVar = 1;         // Accessible
        myObj.protectedVar = 2;      // Accessible
        myObj.defaultVar = 3;        // Accessible
        // Private members are not accessible from AnotherClass

        myObj.publicMethod();        // Accessible
        myObj.protectedMethod();     // Accessible
        myObj.defaultMethod();       // Accessible
        // Private methods are not accessible from AnotherClass
    }
}


// In Subclass.java (a subclass in a different package)
import packageName.ClassA; // Import ClassA to access it

public class Subclass extends ClassA {
    public void accessExample() {
        publicVar = 1;             // Accessible
        protectedVar = 2;          // Accessible
        // defaultVar is not accessible from a subclass in a different package
        // privateVar is not accessible because it's private

        publicMethod();            // Accessible
        protectedMethod();         // Accessible
        // defaultMethod is not accessible from a subclass in a different package
        // privateMethod is not accessible because it's private
    }
}

				
			

Conclusion

Access modifiers in Java play a crucial role in controlling the visibility and accessibility of class members. They help you enforce encapsulation, ensure proper data hiding, and enhance code security by limiting access to only what’s necessary. By understanding and using access modifiers effectively, you can write cleaner and more maintainable Java code.