Functional programming in JavaScript

multitasking designers freelancers networking
0

Introduction to Java Programming

Java has long been a cornerstone in the world of programming, renowned for its versatility, performance, and robust ecosystem. Whether you’re a budding developer stepping into the realm of coding or an experienced programmer aiming to expand your skill set, Java programming offers a wealth of opportunities. This comprehensive guide serves as an Introduction to Java Programming, providing you with foundational knowledge, practical insights, and best practices to help you embark on your Java development journey.

Table of Contents

  1. What is Java?
  2. History of Java
  3. Why Choose Java?
    • Platform Independence
    • Object-Oriented
    • Robust and Secure
    • Extensive Libraries and Frameworks
    • Community Support
  4. Installing Java
    • Installing the Java Development Kit (JDK)
    • Setting Up Environment Variables
    • Choosing an Integrated Development Environment (IDE)
  5. Java Basics
    • Hello, World!
    • Variables and Data Types
    • Operators
    • Control Structures
      • Conditional Statements
      • Loops
  6. Object-Oriented Programming in Java
    • Classes and Objects
    • Inheritance
    • Encapsulation
    • Polymorphism
    • Abstraction
  7. Methods in Java
    • Defining Methods
    • Method Overloading
    • Access Modifiers
  8. Java Data Structures
    • Arrays
    • ArrayList
    • LinkedList
    • HashMap
    • HashSet
  9. Exception Handling
    • Try-Catch Blocks
    • Throw and Throws
    • Finally Block
  10. File Handling
    • Reading Files
    • Writing Files
  11. Introduction to Java Standard Libraries
    • java.lang
    • java.util
    • java.io
    • java.nio
  12. Conclusion
  13. Additional Resources

What is Java?

Java is a high-level, class-based, object-oriented programming language designed to have as few implementation dependencies as possible. Developed by Sun Microsystems (now owned by Oracle Corporation) and released in 1995, Java has become one of the most popular programming languages globally. Its primary philosophy, “Write Once, Run Anywhere” (WORA), ensures that Java applications are portable across different platforms without modification.

Key Features of Java:

  • Platform Independence: Java programs are compiled into bytecode, which can run on any device equipped with a Java Virtual Machine (JVM), making Java applications highly portable.
  • Object-Oriented: Java’s object-oriented nature promotes modularity, reusability, and maintainability by organizing code into classes and objects.
  • Robust and Secure: Java emphasizes early checking for possible errors, strong memory management, and built-in security features, making it reliable for large-scale applications.
  • Multithreaded: Java supports concurrent execution of two or more threads, allowing for efficient CPU utilization and responsive applications.
  • Rich API: Java’s extensive standard library provides a wide range of classes and methods for various functionalities, reducing the need for writing code from scratch.

History of Java

Java was conceived in the early 1990s by James Gosling, Mike Sheridan, and Patrick Naughton at Sun Microsystems. Initially named Oak, Java was developed to address the need for a programming language that could be used across different platforms, particularly for embedded systems and consumer electronics.

Milestones in Java’s Development:

  • 1991: Java development begins at Sun Microsystems, with the goal of creating a platform-independent language.
  • 1995: Java 1.0 is released, introducing the core language features and the Java Virtual Machine (JVM).
  • 1998: Java 2 (J2SE 1.2) is launched, bringing significant enhancements like the Swing GUI toolkit and the Collections Framework.
  • 2004: Introduction of annotations and generics in Java 5, enhancing language expressiveness and type safety.
  • 2014: Oracle acquires Sun Microsystems, becoming the steward of Java.
  • Present: Java continues to evolve with regular updates, the latest being Java 20, focusing on performance, security, and modern programming features.

Why Choose Java?

Java’s enduring popularity is a testament to its strengths and the value it offers to developers and organizations alike. Here are the key reasons why Java remains a top choice for programming:

Platform Independence

Java’s “Write Once, Run Anywhere” (WORA) philosophy ensures that Java applications can run on any device equipped with a JVM. This platform independence eliminates the need for recompiling code for different operating systems, making Java a versatile choice for cross-platform development.

Example:

public class HelloWorld {
    public static void main(String[] args) {
        System.out.println("Hello, World!");
    }
}

This simple program can run on Windows, macOS, Linux, or any other platform with a compatible JVM.

Object-Oriented

Java is inherently object-oriented, promoting principles like encapsulation, inheritance, polymorphism, and abstraction. These principles facilitate code modularity, reusability, and maintainability, allowing developers to build complex applications efficiently.

Example:

public class Car {
    private String model;
    private int year;

    public Car(String model, int year) {
        this.model = model;
        this.year = year;
    }

    public void displayInfo() {
        System.out.println(model + " (" + year + ")");
    }
}

Robust and Secure

Java emphasizes robustness and security through features like automatic garbage collection, strong type checking, and exception handling. The language’s design minimizes common programming errors, reducing the likelihood of runtime crashes and vulnerabilities.

Security Features:

  • Bytecode Verification: Ensures that code adheres to Java’s security standards before execution.
  • Security Manager: Controls access to system resources, preventing unauthorized actions.

Extensive Libraries and Frameworks

Java boasts a vast ecosystem of libraries and frameworks that simplify development across various domains. Whether you’re building web applications, mobile apps, or enterprise systems, Java’s libraries provide the necessary tools and functionalities.

  • Web Development: Spring, Hibernate, JavaServer Faces (JSF)
  • Mobile Development: Android SDK
  • Enterprise Solutions: Java EE, MicroProfile
  • Data Science: Weka, Deeplearning4j

Community Support

Java’s large and active community offers abundant resources, tutorials, and forums for troubleshooting and knowledge sharing. This extensive support network enhances the developer experience, making it easier to learn Java and stay updated with the latest advancements.

Installing Java

Before you can start programming in Java, you need to install the Java Development Kit (JDK) and set up your development environment. Java is compatible with major operating systems, including Windows, macOS, and Linux.

Installing the Java Development Kit (JDK)

The JDK is essential for developing Java applications, providing the compiler (javac), runtime environment, and various development tools.

  1. Download the JDK:
  2. Choose the Appropriate Version:
    • Select the latest stable release (e.g., JDK 20) for new projects.
    • Ensure compatibility with your project’s requirements.
  3. Run the Installer:
    • Follow the installation instructions specific to your operating system.

Setting Up Environment Variables

Configuring environment variables allows you to run Java commands from the command line.

On Windows:

  1. Open System Properties:
    • Right-click on “This PC” > “Properties” > “Advanced system settings”.
  2. Set JAVA_HOME:
    • Click on “Environment Variables”.
    • Under “System variables”, click “New” and set:
      • Variable name: JAVA_HOME
      • Variable value: Path to your JDK installation (e.g., C:\Program Files\Java\jdk-20)
  3. Update PATH Variable:
    • Find the Path variable, select it, and click “Edit”.
    • Click “New” and add %JAVA_HOME%\bin.
  4. Verify Installation:
    • Open Command Prompt and type:
      java -version
      
    • You should see the installed Java version.

On macOS/Linux:

  1. Open Terminal.
  2. Edit Shell Profile:
    • For Bash:
      nano ~/.bash_profile
      
    • For Zsh:
      nano ~/.zshrc
      
  3. Add the Following Lines:
    export JAVA_HOME=/path/to/jdk
    export PATH=$JAVA_HOME/bin:$PATH
    
  4. Apply Changes:
    source ~/.bash_profile
    

    or

    source ~/.zshrc
    
  5. Verify Installation:
    java -version
    

Choosing an Integrated Development Environment (IDE)

An IDE enhances productivity by providing tools like code editors, debuggers, and project management features.

Popular Java IDEs:

  • IntelliJ IDEA: Known for its intelligent code assistance and ergonomic design. Download IntelliJ IDEA
  • Eclipse: Highly customizable and widely used in enterprise environments. Download Eclipse
  • NetBeans: Offers excellent support for Java and other languages. Download NetBeans
  • Visual Studio Code: Lightweight with Java extensions available. Download VS Code

Java Basics

Grasping the fundamental concepts of Java is essential before delving into more complex topics. This section covers basic syntax, variables, data types, operators, and control structures.

Hello, World!

The quintessential first program in any programming language is “Hello, World!”, which demonstrates how to output text to the console.

Example:

public class HelloWorld {
    public static void main(String[] args) {
        System.out.println("Hello, World!");
    }
}

Explanation:

  • public class HelloWorld: Defines a public class named HelloWorld.
  • public static void main(String[] args): The main method, entry point of the program.
  • System.out.println("Hello, World!");: Prints the string to the console.

Running the Program:

  1. Save the Code:
    • Save the above code in a file named HelloWorld.java.
  2. Compile:
    javac HelloWorld.java
    
  3. Run:
    java HelloWorld
    
  4. Output:
    Hello, World!
    

Variables and Data Types

Variables store data that can be used and manipulated throughout your program. Java is a statically typed language, meaning you must declare the data type of a variable before using it.

Primitive Data Types:

  • byte: 8-bit integer
  • short: 16-bit integer
  • int: 32-bit integer
  • long: 64-bit integer
  • float: Single-precision 32-bit floating point
  • double: Double-precision 64-bit floating point
  • char: Single 16-bit Unicode character
  • boolean: true or false

Example:

public class VariablesDemo {
    public static void main(String[] args) {
        int age = 25;
        double salary = 75000.50;
        char grade = 'A';
        boolean isEmployed = true;

        System.out.println("Age: " + age);
        System.out.println("Salary: $" + salary);
        System.out.println("Grade: " + grade);
        System.out.println("Employed: " + isEmployed);
    }
}

Output:

Age: 25
Salary: $75000.5
Grade: A
Employed: true

Operators

Operators perform operations on variables and values. Java includes several types of operators:

  • Arithmetic Operators: +, -, *, /, %
  • Assignment Operators: =, +=, -=, *=, /=, %=
  • Comparison Operators: ==, !=, >, <, >=, <=
  • Logical Operators: &&, ||, !
  • Increment/Decrement Operators: ++, --

Arithmetic Operators Example:

public class ArithmeticOperators {
    public static void main(String[] args) {
        int a = 10;
        int b = 3;

        System.out.println("a + b = " + (a + b)); // 13
        System.out.println("a - b = " + (a - b)); // 7
        System.out.println("a * b = " + (a * b)); // 30
        System.out.println("a / b = " + (a / b)); // 3
        System.out.println("a % b = " + (a % b)); // 1
    }
}

Output:

a + b = 13
a - b = 7
a * b = 30
a / b = 3
a % b = 1

Control Structures

Control structures dictate the flow of a program based on certain conditions or repeated actions.

Conditional Statements

Conditional statements execute code blocks based on whether a condition is true or false.

Example:

public class ConditionalDemo {
    public static void main(String[] args) {
        int temperature = 30;

        if (temperature > 25) {
            System.out.println("It's hot outside.");
        } else if (temperature > 15) {
            System.out.println("It's warm outside.");
        } else {
            System.out.println("It's cold outside.");
        }
    }
}

Output:

It's hot outside.

Loops

Loops allow you to execute a block of code multiple times.

For Loop Example:

public class ForLoopDemo {
    public static void main(String[] args) {
        String[] fruits = {"Apple", "Banana", "Cherry"};

        for (int i = 0; i < fruits.length; i++) {
            System.out.println(fruits[i]);
        }
    }
}

Output:

Apple
Banana
Cherry

Enhanced For Loop Example (For-Each):

public class ForEachDemo {
    public static void main(String[] args) {
        String[] fruits = {"Apple", "Banana", "Cherry"};

        for (String fruit : fruits) {
            System.out.println(fruit);
        }
    }
}

Output:

Apple
Banana
Cherry

While Loop Example:

public class WhileLoopDemo {
    public static void main(String[] args) {
        int count = 0;

        while (count < 5) {
            System.out.println("Count: " + count);
            count++;
        }
    }
}

Output:

Count: 0
Count: 1
Count: 2
Count: 3
Count: 4

Summary of Control Structures

Control Structure Description
if / else if / else Executes code based on conditions
switch Selects execution path based on a variable’s value
for Repeats a block of code a specific number of times
while Repeats a block of code while a condition is true
do-while Executes a block of code at least once and then repeats while a condition is true

Object-Oriented Programming in Java

Java is inherently object-oriented, providing a structured approach to programming by modeling real-world entities through classes and objects. Understanding the core principles of Object-Oriented Programming (OOP) is essential for writing efficient and maintainable Java code.

Key OOP Principles:

  1. Encapsulation
  2. Abstraction
  3. Inheritance
  4. Polymorphism

Classes and Objects

Classes are blueprints for creating objects. They encapsulate data for the object and methods to manipulate that data.

Defining a Class:

public class Car {
    // Attributes (Fields)
    private String model;
    private int year;
    private double price;

    // Constructor
    public Car(String model, int year, double price) {
        this.model = model;
        this.year = year;
        this.price = price;
    }

    // Method
    public void displayInfo() {
        System.out.println(model + " (" + year + ") - $" + price);
    }
}

Creating an Object:

public class CarDemo {
    public static void main(String[] args) {
        Car myCar = new Car("Toyota Camry", 2020, 24000.00);
        myCar.displayInfo();
    }
}

Output:

Toyota Camry (2020) - $24000.0

Inheritance

Inheritance allows a class (subclass) to inherit attributes and methods from another class (superclass), promoting code reuse and hierarchical relationships.

Single Inheritance Example:

// Superclass
public class Animal {
    String name;

    public Animal(String name) {
        this.name = name;
    }

    public void speak() {
        System.out.println(name + " makes a sound.");
    }
}

// Subclass
public class Dog extends Animal {
    public Dog(String name) {
        super(name);
    }

    // Overriding the speak method
    @Override
    public void speak() {
        System.out.println(name + " says woof!");
    }
}

// Demo
public class InheritanceDemo {
    public static void main(String[] args) {
        Dog myDog = new Dog("Buddy");
        myDog.speak(); // Output: Buddy says woof!
    }
}

Encapsulation

Encapsulation restricts direct access to an object’s data, bundling it with methods that operate on that data. This promotes data integrity and security.

Example:

public class BankAccount {
    // Private attributes
    private double balance;

    // Constructor
    public BankAccount(double initialBalance) {
        this.balance = initialBalance;
    }

    // Getter method
    public double getBalance() {
        return balance;
    }

    // Setter method for deposit
    public void deposit(double amount) {
        if (amount > 0) {
            balance += amount;
            System.out.println("Deposited: $" + amount);
        } else {
            System.out.println("Invalid deposit amount.");
        }
    }

    // Method to withdraw funds
    public void withdraw(double amount) {
        if (amount > 0 && amount <= balance) {
            balance -= amount;
            System.out.println("Withdrew: $" + amount);
        } else {
            System.out.println("Invalid withdrawal amount.");
        }
    }
}

// Demo
public class EncapsulationDemo {
    public static void main(String[] args) {
        BankAccount account = new BankAccount(1000.00);
        account.deposit(500.00);    // Deposited: $500.0
        account.withdraw(200.00);   // Withdrew: $200.0
        System.out.println("Current Balance: $" + account.getBalance()); // Current Balance: $1300.0
    }
}

Polymorphism

Polymorphism allows objects of different classes to be treated as instances of a common superclass, enabling flexibility and interchangeable code.

Example:

// Superclass
public class Shape {
    public void draw() {
        System.out.println("Drawing a shape.");
    }
}

// Subclass 1
public class Circle extends Shape {
    @Override
    public void draw() {
        System.out.println("Drawing a circle.");
    }
}

// Subclass 2
public class Rectangle extends Shape {
    @Override
    public void draw() {
        System.out.println("Drawing a rectangle.");
    }
}

// Demo
public class PolymorphismDemo {
    public static void main(String[] args) {
        Shape shape1 = new Circle();
        Shape shape2 = new Rectangle();

        shape1.draw(); // Output: Drawing a circle.
        shape2.draw(); // Output: Drawing a rectangle.
    }
}

Abstraction

Abstraction simplifies complex systems by modeling classes appropriate to the problem, hiding unnecessary details, and exposing only relevant functionalities.

Using Abstract Classes:

// Abstract class
public abstract class Vehicle {
    String brand;

    public Vehicle(String brand) {
        this.brand = brand;
    }

    // Abstract method
    public abstract void honk();
}

// Subclass
public class Car extends Vehicle {
    public Car(String brand) {
        super(brand);
    }

    @Override
    public void honk() {
        System.out.println(brand + " car honks: Beep Beep!");
    }
}

// Demo
public class AbstractionDemo {
    public static void main(String[] args) {
        Car myCar = new Car("Toyota");
        myCar.honk(); // Output: Toyota car honks: Beep Beep!
    }
}

Methods in Java

Methods are blocks of code that perform specific tasks. They enhance modularity, readability, and reusability of code.

Defining Methods

Syntax:

public returnType methodName(parameters) {
    // Method body
}

Example:

public class MathOperations {
    // Method to add two numbers
    public int add(int a, int b) {
        return a + b;
    }

    // Method to multiply two numbers
    public int multiply(int a, int b) {
        return a * b;
    }
}

// Demo
public class MethodDemo {
    public static void main(String[] args) {
        MathOperations math = new MathOperations();
        int sum = math.add(5, 3);
        int product = math.multiply(5, 3);

        System.out.println("Sum: " + sum);        // Sum: 8
        System.out.println("Product: " + product); // Product: 15
    }
}

Method Overloading

Method overloading allows multiple methods with the same name but different parameters within the same class. It enhances readability and usability.

Example:

public class Display {
    // Overloaded method with no parameters
    public void show() {
        System.out.println("No parameters.");
    }

    // Overloaded method with one parameter
    public void show(String message) {
        System.out.println("Message: " + message);
    }

    // Overloaded method with two parameters
    public void show(String message, int number) {
        System.out.println("Message: " + message + ", Number: " + number);
    }
}

// Demo
public class OverloadingDemo {
    public static void main(String[] args) {
        Display display = new Display();
        display.show();                          // No parameters.
        display.show("Hello, Java!");            // Message: Hello, Java!
        display.show("Java Overloading", 10);    // Message: Java Overloading, Number: 10
    }
}

Output:

No parameters.
Message: Hello, Java!
Message: Java Overloading, Number: 10

Access Modifiers

Access modifiers control the visibility of classes, methods, and variables. Java provides four access levels:

  • public: Accessible from any other class.
  • protected: Accessible within the same package and subclasses.
  • default (no modifier): Accessible only within the same package.
  • private: Accessible only within the declared class.

Example:

public class AccessModifiersDemo {
    public int publicVar = 1;
    protected int protectedVar = 2;
    int defaultVar = 3; // default access
    private int privateVar = 4;

    public void display() {
        System.out.println("Public Variable: " + publicVar);
        System.out.println("Protected Variable: " + protectedVar);
        System.out.println("Default Variable: " + defaultVar);
        System.out.println("Private Variable: " + privateVar);
    }
}

// Demo in the same package
public class AccessDemo {
    public static void main(String[] args) {
        AccessModifiersDemo obj = new AccessModifiersDemo();
        obj.display();

        // Accessing variables directly
        System.out.println("Direct Access:");
        System.out.println("Public: " + obj.publicVar);        // Accessible
        System.out.println("Protected: " + obj.protectedVar);  // Accessible
        System.out.println("Default: " + obj.defaultVar);      // Accessible
        // System.out.println("Private: " + obj.privateVar);   // Not accessible, will cause an error
    }
}

Output:

Public Variable: 1
Protected Variable: 2
Default Variable: 3
Private Variable: 4
Direct Access:
Public: 1
Protected: 2
Default: 3

Summary of Access Modifiers

Modifier Class Package Subclass World
public Yes Yes Yes Yes
protected Yes Yes Yes No
Default Yes Yes No No
private Yes No No No

Java Data Structures

Efficient data management is crucial for building high-performance applications. Java provides a variety of data structures to store and manipulate data effectively.

Arrays

Arrays are fixed-size, ordered collections of elements of the same type.

Example:

public class ArrayDemo {
    public static void main(String[] args) {
        // Declaring and initializing an array
        int[] numbers = {10, 20, 30, 40, 50};

        // Accessing elements
        System.out.println("First Element: " + numbers[0]); // 10

        // Iterating through the array
        System.out.println("All Elements:");
        for (int num : numbers) {
            System.out.println(num);
        }
    }
}

Output:

First Element: 10
All Elements:
10
20
30
40
50

Limitations:

  • Fixed Size: Cannot be resized after creation.
  • Homogeneous: Stores elements of the same data type.

ArrayList

ArrayList is a resizable array implementation of the List interface. It allows dynamic resizing and provides methods to manipulate the list.

Example:

import java.util.ArrayList;

public class ArrayListDemo {
    public static void main(String[] args) {
        // Creating an ArrayList
        ArrayList<String> fruits = new ArrayList<>();

        // Adding elements
        fruits.add("Apple");
        fruits.add("Banana");
        fruits.add("Cherry");

        // Accessing elements
        System.out.println("First Fruit: " + fruits.get(0)); // Apple

        // Iterating through the ArrayList
        System.out.println("All Fruits:");
        for (String fruit : fruits) {
            System.out.println(fruit);
        }

        // Removing an element
        fruits.remove("Banana");
        System.out.println("After Removal: " + fruits);
    }
}

Output:

First Fruit: Apple
All Fruits:
Apple
Banana
Cherry
After Removal: [Apple, Cherry]

LinkedList

LinkedList is a doubly-linked list implementation of the List and Deque interfaces. It provides efficient insertions and deletions but slower access compared to ArrayList.

Example:

import java.util.LinkedList;

public class LinkedListDemo {
    public static void main(String[] args) {
        // Creating a LinkedList
        LinkedList<String> animals = new LinkedList<>();

        // Adding elements
        animals.add("Dog");
        animals.add("Cat");
        animals.add("Elephant");

        // Adding elements at specific positions
        animals.addFirst("Lion");
        animals.addLast("Tiger");

        // Accessing elements
        System.out.println("First Animal: " + animals.getFirst()); // Lion
        System.out.println("Last Animal: " + animals.getLast());   // Tiger

        // Iterating through the LinkedList
        System.out.println("All Animals:");
        for (String animal : animals) {
            System.out.println(animal);
        }

        // Removing an element
        animals.remove("Cat");
        System.out.println("After Removal: " + animals);
    }
}

Output:

First Animal: Lion
Last Animal: Tiger
All Animals:
Lion
Dog
Cat
Elephant
Tiger
After Removal: [Lion, Dog, Elephant, Tiger]

HashMap

HashMap is a hash table-based implementation of the Map interface. It stores key-value pairs and allows fast retrieval based on keys.

Example:

import java.util.HashMap;

public class HashMapDemo {
    public static void main(String[] args) {
        // Creating a HashMap
        HashMap<String, Integer> scores = new HashMap<>();

        // Adding key-value pairs
        scores.put("Alice", 85);
        scores.put("Bob", 92);
        scores.put("Charlie", 78);

        // Accessing a value by key
        System.out.println("Bob's Score: " + scores.get("Bob")); // 92

        // Iterating through the HashMap
        System.out.println("All Scores:");
        for (String key : scores.keySet()) {
            System.out.println(key + ": " + scores.get(key));
        }

        // Removing a key-value pair
        scores.remove("Charlie");
        System.out.println("After Removal: " + scores);
    }
}

Output:

Bob's Score: 92
All Scores:
Alice: 85
Bob: 92
Charlie: 78
After Removal: {Alice=85, Bob=92}

HashSet

HashSet is a hash table-based implementation of the Set interface. It stores unique elements and does not allow duplicates.

Example:

import java.util.HashSet;

public class HashSetDemo {
    public static void main(String[] args) {
        // Creating a HashSet
        HashSet<String> uniqueNames = new HashSet<>();

        // Adding elements
        uniqueNames.add("Alice");
        uniqueNames.add("Bob");
        uniqueNames.add("Charlie");
        uniqueNames.add("Alice"); // Duplicate, will not be added

        // Iterating through the HashSet
        System.out.println("Unique Names:");
        for (String name : uniqueNames) {
            System.out.println(name);
        }

        // Removing an element
        uniqueNames.remove("Bob");
        System.out.println("After Removal: " + uniqueNames);
    }
}

Output:

Unique Names:
Alice
Bob
Charlie
After Removal: [Alice, Charlie]

Exception Handling

Exception handling ensures that your program can gracefully handle unexpected events or errors without crashing.

Try-Catch Blocks

The try block contains code that might throw an exception, while the catch block handles the exception.

Example:

public class ExceptionDemo {
    public static void main(String[] args) {
        try {
            int result = 10 / 0; // This will cause ArithmeticException
            System.out.println("Result: " + result);
        } catch (ArithmeticException e) {
            System.out.println("Error: Division by zero is not allowed.");
        }
    }
}

Output:

Error: Division by zero is not allowed.

Throw and Throws

  • throw: Used to explicitly throw an exception.
  • throws: Declares that a method might throw specified exceptions.

Example of throw:

public class ThrowDemo {
    public static void main(String[] args) {
        try {
            validateAge(15);
        } catch (Exception e) {
            System.out.println(e.getMessage());
        }
    }

    public static void validateAge(int age) throws Exception {
        if (age < 18) {
            throw new Exception("Age must be at least 18.");
        } else {
            System.out.println("Access granted.");
        }
    }
}

Output:

Age must be at least 18.

Finally Block

The finally block contains code that executes regardless of whether an exception was thrown or caught, typically used for resource cleanup.

Example:

public class FinallyDemo {
    public static void main(String[] args) {
        try {
            int[] numbers = {1, 2, 3};
            System.out.println(numbers[5]); // This will cause ArrayIndexOutOfBoundsException
        } catch (ArrayIndexOutOfBoundsException e) {
            System.out.println("Error: Index out of bounds.");
        } finally {
            System.out.println("Execution completed.");
        }
    }
}

Output:

Error: Index out of bounds.
Execution completed.

File Handling

Java provides classes for reading from and writing to files, enabling data persistence and manipulation.

Reading Files

The BufferedReader class, combined with FileReader, is commonly used for reading text files efficiently.

Example:

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;

public class FileReadDemo {
    public static void main(String[] args) {
        String filePath = "example.txt";

        try (BufferedReader br = new BufferedReader(new FileReader(filePath))) {
            String line;
            while ((line = br.readLine()) != null) {
                System.out.println(line);
            }
        } catch (IOException e) {
            System.out.println("Error: Unable to read the file.");
        }
    }
}

Explanation:

  • BufferedReader: Buffers the characters for efficient reading.
  • FileReader: Reads character files.
  • Try-with-resources: Ensures that the reader is closed automatically.

Writing Files

The BufferedWriter class, along with FileWriter, is used for writing text to files.

Example:

import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;

public class FileWriteDemo {
    public static void main(String[] args) {
        String filePath = "output.txt";
        String content = "Hello, Java!\nWriting to a file is easy.";

        try (BufferedWriter bw = new BufferedWriter(new FileWriter(filePath))) {
            bw.write(content);
            System.out.println("File written successfully.");
        } catch (IOException e) {
            System.out.println("Error: Unable to write to the file.");
        }
    }
}

Output:

File written successfully.

Appending to a File:

import java.io.BufferedWriter;
import java.io.FileWriter;
import java.io.IOException;

public class FileAppendDemo {
    public static void main(String[] args) {
        String filePath = "output.txt";
        String additionalContent = "\nAppending a new line.";

        try (BufferedWriter bw = new BufferedWriter(new FileWriter(filePath, true))) {
            bw.write(additionalContent);
            System.out.println("Content appended successfully.");
        } catch (IOException e) {
            System.out.println("Error: Unable to append to the file.");
        }
    }
}

Output:

Content appended successfully.

Introduction to Java Standard Libraries

Java’s Standard Library provides a rich set of classes and interfaces for various functionalities, eliminating the need to write common code from scratch.

java.lang

The java.lang package is fundamental to Java programming, providing essential classes.

Key Classes:

  • String: Represents immutable character strings.
  • Math: Provides basic math functions.
  • System: Contains facilities related to the runtime environment.
  • Object: The root of the class hierarchy.

Example:

public class LangDemo {
    public static void main(String[] args) {
        String greeting = "Hello, Java!";
        double sqrtValue = Math.sqrt(25);

        System.out.println(greeting);          // Hello, Java!
        System.out.println("Square Root: " + sqrtValue); // Square Root: 5.0
    }
}

java.util

The java.util package contains utility classes for collections, date and time operations, random number generation, and more.

Key Classes:

  • ArrayList: Resizable array implementation of the List interface.
  • HashMap: Hash table-based implementation of the Map interface.
  • Scanner: Facilitates user input.
  • Date and Calendar: Handle date and time.

Example:

import java.util.ArrayList;
import java.util.Scanner;

public class UtilDemo {
    public static void main(String[] args) {
        // Using ArrayList
        ArrayList<String> colors = new ArrayList<>();
        colors.add("Red");
        colors.add("Green");
        colors.add("Blue");

        System.out.println("Colors: " + colors);

        // Using Scanner for user input
        Scanner scanner = new Scanner(System.in);
        System.out.print("Enter your name: ");
        String name = scanner.nextLine();
        System.out.println("Hello, " + name + "!");
    }
}

java.io

The java.io package provides classes for system input and output through data streams, serialization, and the file system.

Key Classes:

  • File: Represents file and directory pathnames.
  • FileReader and FileWriter: Read from and write to files.
  • BufferedReader and BufferedWriter: Buffer input and output for efficiency.
  • InputStream and OutputStream: Handle byte streams.

Example:

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;

public class IODemo {
    public static void main(String[] args) {
        String filePath = "sample.txt";

        try (BufferedReader br = new BufferedReader(new FileReader(filePath))) {
            String line;
            while ((line = br.readLine()) != null) {
                System.out.println(line);
            }
        } catch (IOException e) {
            System.out.println("Error: Unable to read the file.");
        }
    }
}

java.nio

The java.nio (New I/O) package offers advanced features for I/O operations, including non-blocking I/O, buffers, channels, and selectors, enhancing performance and scalability.

Key Classes:

  • Path: Represents file and directory paths.
  • Files: Contains methods for file manipulation.
  • ByteBuffer: Handles byte buffers for I/O operations.

Example:

import java.nio.file.Files;
import java.nio.file.Path;
import java.nio.file.Paths;
import java.io.IOException;

public class NIODemo {
    public static void main(String[] args) {
        Path filePath = Paths.get("nio_sample.txt");
        String content = "Hello, Java NIO!";

        try {
            // Writing to a file
            Files.write(filePath, content.getBytes());
            System.out.println("File written successfully.");

            // Reading from a file
            String readContent = Files.readString(filePath);
            System.out.println("File Content: " + readContent);
        } catch (IOException e) {
            System.out.println("Error: " + e.getMessage());
        }
    }
}

Output:

File written successfully.
File Content: Hello, Java NIO!

Conclusion

Java remains a powerhouse in the programming world, offering a blend of performance, portability, and a rich ecosystem that caters to a wide range of applications. From building mobile apps and web servers to handling large-scale enterprise systems, Java’s robust features and extensive libraries make it a go-to language for developers worldwide.

This Introduction to Java Programming has covered the essential aspects of Java, including its history, key features, installation, basic syntax, object-oriented principles, data structures, exception handling, and standard libraries. Armed with this foundational knowledge, you’re well-equipped to delve deeper into Java’s advanced topics and start building your own applications.

As you continue your Java journey, consider exploring frameworks like Spring and Hibernate, delve into Java EE for enterprise solutions, or venture into Android development. Practice consistently, engage with the vibrant Java community, and leverage the plethora of resources available to enhance your skills and stay updated with the latest advancements in Java technology.

Additional Resources


Embark on your Java programming journey today and unlock endless possibilities in the world of software development, enterprise solutions, and beyond. With dedication and the right resources, mastering Java can open doors to a myriad of career opportunities and innovative projects.