Encapsulation is a fundamental concept in object-oriented programming (OOP) that involves bundling the data (attributes) and methods (functions) that operate on the data into a single unit or class. It also restricts direct access to some of an object's components, which can prevent the accidental modification of data. In this tutorial, we'll explore how encapsulation works in Java using getter and setter methods, why it's important, and how to implement it effectively.
Encapsulation is one of the four pillars of OOP, alongside inheritance, polymorphism, and abstraction. It helps in protecting the integrity of an object by restricting access to its internal state and providing controlled ways to interact with it. This not only makes the code more secure but also easier to maintain and extend.
In Java, encapsulation is achieved by making the class attributes private and providing public getter and setter methods to access and modify these attributes. This way, you can control how the data is accessed and modified, ensuring that it remains in a valid state.
Encapsulation is the practice of hiding the internal implementation details of an object and exposing only the necessary parts through well-defined interfaces. It provides several benefits:
To implement encapsulation in Java, follow these steps:
Let's create a simple Person class with encapsulation.
1public class Person {2// Private attributes3private String name;4private int age;56// Getter for name7public String getName() {8return name;9};1011// Setter for name12public void setName(String name) {13this.name = name;14}1516// Getter for age17public int getAge() {18return age;19}2021// Setter for age with validation22public void setAge(int age) {23if (age > 0) {24this.age = age;25} else {26System.out.println("Age must be positive.");27}28}29}
In this example, the name and age attributes are private, meaning they cannot be accessed directly from outside the class. The getName() and getAge() methods provide read access to these attributes, while the setName(String name) and setAge(int age) methods allow controlled modification.
Now, let's create a Main class to use the Person class with encapsulation.
1public class Main {2public static void main(String[] args) {3Person person = new Person();45// Setting values using setters6person.setName("John Doe");7person.setAge(30);89// Getting values using getters10System.out.println("Name: " + person.getName());11System.out.println("Age: " + person.getAge());12}13}
Name: John Doe Age: 30
In this example, we create an instance of the Person class and use the setter methods to set the name and age. We then retrieve these values using the getter methods and print them.
Let's create a more complex example that demonstrates encapsulation in a real-world scenario. We'll create a BankAccount class with encapsulation, including methods to deposit and withdraw money.
1public class BankAccount {2private String accountNumber;3private double balance;45// Constructor6public BankAccount(String accountNumber) {7this.accountNumber = accountNumber;8this.balance = 0.0;9}1011// Getter for account number12public String getAccountNumber() {13return accountNumber;14}1516// Getter for balance17public double getBalance() {18return balance;19}2021// Method to deposit money22public void deposit(double amount) {23if (amount > 0) {24balance += amount;25System.out.println("Deposited: $" + amount);26} else {27System.out.println("Deposit amount must be positive.");28}29}3031// Method to withdraw money32public boolean withdraw(double amount) {33if (amount > 0 && amount <= balance) {34balance -= amount;35System.out.println("Withdrew: $" + amount);36return true;37} else {38System.out.println("Insufficient funds or invalid amount.");39return false;40}41}42}
1public class Main {2public static void main(String[] args) {3BankAccount account = new BankAccount("123456789");45// Deposit money6account.deposit(1000);78// Withdraw money9account.withdraw(500);10account.withdraw(600); // This will fail due to insufficient funds1112// Check balance13System.out.println("Current Balance: $" + account.getBalance());14}15}
Deposited: $1000.0 Withdrew: $500.0 Insufficient funds or invalid amount. Current Balance: $500.0
In this example, the BankAccount class encapsulates the account number and balance. The deposit and withdraw methods provide controlled ways to modify the balance, ensuring that only valid transactions are processed.
Now that you understand encapsulation in Java, the next step is to learn about Java Packages / API. Packages help organize classes and interfaces into namespaces, making it easier to manage large projects. APIs (Application Programming Interfaces) provide a way for different software components to communicate with each other. Understanding packages and APIs will further enhance your ability to build robust and scalable Java applications.
Stay tuned for the next tutorial where we'll dive deeper into Java Packages and APIs!