core_java_unit_III

Inheritance, Package and Collection

3.1 Overview of Inheritance

Inheritance is a fundamental concept in object-oriented programming that allows a new class (derived class or subclass) to inherit attributes and methods from an existing class (base class or superclass). This promotes code reuse and establishes a natural hierarchy between classes.

Key Points:

  • Superclass: The class being inherited from.

  • Subclass: The class that inherits from the superclass.

  • extends Keyword: Used to create a subclass from a superclass.

  • Method Overriding: A subclass can provide a specific implementation of a method already defined in its superclass.

  • Access Specifiers: Inheritance respects access control modifiers (private, protected, public).

3.2 Inheritance in Constructors

Constructors are not inherited in the same way as methods. However, a subclass constructor can call a superclass constructor using the super keyword. This ensures that the initialization defined in the superclass is performed.

Example:

class Animal {

String name;


// Superclass constructor

Animal(String name) {

this.name = name;

}


void display() {

System.out.println("Animal name: " + name);

}

}


class Dog extends Animal {

String breed;


// Subclass constructor

Dog(String name, String breed) {

super(name); // Calls the superclass constructor

this.breed = breed;

}


@Override

void display() {

super.display(); // Calls the superclass method

System.out.println("Dog breed: " + breed);

}

}


public class InheritanceExample {

public static void main(String[] args) {

Dog dog = new Dog("Buddy", "Golden Retriever");

dog.display();

}

}

3.3 Inheriting Data Members and Methods

When a subclass inherits from a superclass, it inherits all non-private data members and methods. The subclass can use these members and methods directly or override them to provide specific functionality.

Example:

java

Copy code

class Animal {

// Data members

protected String name;

protected int age;


// Method

void eat() {

System.out.println(name + " is eating.");

}

}


class Dog extends Animal {

// Additional data member

private String breed;


// Constructor

Dog(String name, int age, String breed) {

this.name = name; // Inherited data member

this.age = age; // Inherited data member

this.breed = breed;

}


// Overridden method

@Override

void eat() {

System.out.println(name + " the " + breed + " is eating.");

}


// Additional method

void bark() {

System.out.println(name + " is barking.");

}

}


public class InheritanceExample {

public static void main(String[] args) {

Dog dog = new Dog("Buddy", 5, "Golden Retriever");

dog.eat(); // Calls overridden method

dog.bark(); // Calls subclass method

}

}

Key Points:

  • Data Members: Subclasses inherit all non-private data members. Private members are not accessible directly, but they can be accessed via public/protected getter and setter methods.

  • Methods: Subclasses inherit all non-private methods. They can use these methods as is or override them to change their behavior.



3.4 Multilevel Inheritance

Multilevel inheritance is a type of inheritance where a class is derived from another derived class, forming a chain of inheritance. In this structure, the subclass inherits the properties and methods of its superclass, which in turn inherits from another superclass.

Method Overriding in Multilevel Inheritance

Method overriding occurs when a subclass provides a specific implementation for a method that is already defined in its superclass. In multilevel inheritance, any subclass can override a method from any superclass in the inheritance chain.

Handling Multilevel Constructors

When dealing with multilevel inheritance, constructors from each superclass in the hierarchy must be called to ensure proper initialization. The super keyword is used to call the constructor of the immediate superclass.

Example

class Animal {

String name;


Animal(String name) {

this.name = name;

System.out.println("Animal constructor called");

}


void eat() {

System.out.println(name + " is eating.");

}

}


class Mammal extends Animal {

Mammal(String name) {

super(name); // Call to Animal's constructor

System.out.println("Mammal constructor called");

}


@Override

void eat() {

System.out.println(name + " the mammal is eating.");

}

}


class Dog extends Mammal {

Dog(String name) {

super(name); // Call to Mammal's constructor

System.out.println("Dog constructor called");

}


@Override

void eat() {

System.out.println(name + " the dog is eating.");

}

}


public class MultilevelInheritanceExample {

public static void main(String[] args) {

Dog dog = new Dog("Buddy");

dog.eat();

}

}

3.5 Use of super and final Keyword

super Keyword

The super keyword in Java is used to refer to the immediate superclass of a current object. It can be used to:

  • Call a superclass constructor.

  • Call a superclass method.

Example of super Keyword

class Animal {

void eat() {

System.out.println("Animal is eating.");

}

}


class Dog extends Animal {

@Override

void eat() {

super.eat(); // Calls the superclass method

System.out.println("Dog is eating.");

}

}


public class SuperExample {

public static void main(String[] args) {

Dog dog = new Dog();

dog.eat();

}

}

final Keyword

The final keyword can be used with classes, methods, and variables to restrict their modification:

  • final class: A class that cannot be subclassed.

  • final method: A method that cannot be overridden.

  • final variable: A variable whose value cannot be changed once assigned.

Example of final Keyword

final class Animal {

final void eat() {

System.out.println("Animal is eating.");

}

}


class Dog { // Cannot extend Animal because Animal is final

// void eat() { // Cannot override because eat() is final in Animal

// System.out.println("Dog is eating.");

// }

}


public class FinalExample {

public static void main(String[] args) {

Animal animal = new Animal();

animal.eat();

}

}

3.6 Interface

An interface in Java is a reference type, similar to a class, that can contain only constants, method signatures, default methods, static methods, and nested types. Interfaces cannot contain instance fields or constructors. They are used to specify a contract that classes must follow.

Key Points

  • Method Signatures: An interface defines methods that implementing classes must provide.

  • Multiple Inheritance: A class can implement multiple interfaces, providing a way to achieve multiple inheritance.

  • Default Methods: Methods in interfaces with a default implementation.

  • Static Methods: Methods in interfaces that are static.

Example of an Interface

interface Animal {

void eat();

void sleep();

}


class Dog implements Animal {

@Override

public void eat() {

System.out.println("Dog is eating.");

}


@Override

public void sleep() {

System.out.println("Dog is sleeping.");

}

}


public class InterfaceExample {

public static void main(String[] args) {

Dog dog = new Dog();

dog.eat();

dog.sleep();

}

}

Multiple Interface Implementation

interface Animal {

void eat();

}


interface Pet {

void play();

}


class Dog implements Animal, Pet {

@Override

public void eat() {

System.out.println("Dog is eating.");

}


@Override

public void play() {

System.out.println("Dog is playing.");

}

}


public class MultipleInterfaceExample {

public static void main(String[] args) {

Dog dog = new Dog();

dog.eat();

dog.play();

}

}



Multilevel Inheritance: Allows classes to inherit from other derived classes. Constructors and methods can be overridden in the inheritance chain.

super Keyword: Used to call superclass constructors and methods.

final Keyword: Prevents classes from being subclassed, methods from being overridden, and variables from being reassigned.

Interfaces: Define a contract that implementing classes must follow, supporting multiple inheritance and abstract method definitions.



3.7 Creation and Implementation of an Interface, Interface Reference

Creating an Interface

An interface in Java is created using the interface keyword. It can contain abstract methods, default methods, static methods, and constants.

Example:

interface Animal {

void eat();

void sleep();

}

Implementing an Interface

A class implements an interface using the implements keyword and provides concrete implementations for all the interface methods.

Example:

class Dog implements Animal {

@Override

public void eat() {

System.out.println("Dog is eating.");

}


@Override

public void sleep() {

System.out.println("Dog is sleeping.");

}

}


public class InterfaceExample {

public static void main(String[] args) {

Dog dog = new Dog();

dog.eat();

dog.sleep();

}

}

Interface Reference

An interface reference can refer to any object that implements the interface. This allows for polymorphic behavior.

Example:

public class InterfaceReferenceExample {

public static void main(String[] args) {

Animal animal = new Dog(); // Interface reference

animal.eat();

animal.sleep();

}

}

3.8 Interface Inheritance

Interfaces can extend other interfaces, allowing for a hierarchical structure. An interface can extend multiple interfaces, enabling multiple inheritance.

Example:

interface Animal {

void eat();

}


interface Mammal extends Animal {

void walk();

}


class Dog implements Mammal {

@Override

public void eat() {

System.out.println("Dog is eating.");

}


@Override

public void walk() {

System.out.println("Dog is walking.");

}

}


public class InterfaceInheritanceExample {

public static void main(String[] args) {

Dog dog = new Dog();

dog.eat();

dog.walk();

}

}

3.9 Dynamic Method Dispatch

Dynamic method dispatch, also known as runtime polymorphism, is the mechanism by which a call to an overridden method is resolved at runtime rather than compile-time. This is achieved through method overriding and interface references.

Example:

class Animal {

void sound() {

System.out.println("Animal makes a sound");

}

}


class Dog extends Animal {

@Override

void sound() {

System.out.println("Dog barks");

}

}


class Cat extends Animal {

@Override

void sound() {

System.out.println("Cat meows");

}

}


public class DynamicMethodDispatchExample {

public static void main(String[] args) {

Animal animal;


animal = new Dog();

animal.sound(); // Calls Dog's sound method


animal = new Cat();

animal.sound(); // Calls Cat's sound method

}

}

Summary

  • Creation and Implementation of an Interface: Interfaces are created using the interface keyword. Classes implement interfaces using the implements keyword, and an interface reference can refer to any object that implements the interface.

  • Interface Inheritance: Interfaces can extend other interfaces, enabling hierarchical and multiple inheritance structures.

  • Dynamic Method Dispatch: Allows method calls to be resolved at runtime. This is achieved through method overriding and interface references, enabling polymorphic behavior.



3.10 Abstract Class

An abstract class in Java is a class that cannot be instantiated on its own and is meant to be subclassed. It may contain abstract methods, which are declared but not implemented in the abstract class. Subclasses must implement these abstract methods.

Creating an Abstract Class

An abstract class is created using the abstract keyword.

abstract class Animal {

abstract void sound(); // Abstract method

}

Implementing an Abstract Class

Subclasses of an abstract class must provide concrete implementations for all abstract methods, or they themselves must be declared abstract.

class Dog extends Animal {

@Override

void sound() {

System.out.println("Dog barks");

}

}

3.11 Comparison between Abstract Class and Interface

Abstract Class

  • Can have constructors.

  • Can have both abstract and non-abstract methods.

  • Can have member variables that can be inherited.

  • Supports single inheritance only.

  • Can provide default implementations for methods.

  • Can have access modifiers for methods and fields.

Interface

  • Cannot have constructors.

  • Can only have abstract methods (before Java 8).

  • Cannot have member variables, only constants.

  • Supports multiple inheritance.

  • Cannot provide default implementations for methods (before Java 8), but default and static methods are allowed in Java 8 and later.

  • All methods are implicitly public and abstract.

3.12 Access Control

Access control in Java determines the accessibility of classes, methods, and variables from different parts of the program.

Access Modifiers

  • Private: Accessible only within the same class.

  • Default (Package-private): Accessible only within the same package.

  • Protected: Accessible within the same package and by subclasses (even if they are in a different package).

  • Public: Accessible from anywhere.

Example:

public class AccessControlExample {

private int privateVar;

int defaultVar; // Package-private

protected int protectedVar;

public int publicVar;


private void privateMethod() {

System.out.println("Private method");

}


void defaultMethod() { // Package-private

System.out.println("Default method");

}


protected void protectedMethod() {

System.out.println("Protected method");

}


public void publicMethod() {

System.out.println("Public method");

}

}

Accessing Members

public class Main {

public static void main(String[] args) {

AccessControlExample obj = new AccessControlExample();


// Accessing variables

obj.defaultVar = 10;

obj.protectedVar = 20;

obj.publicVar = 30;


// Accessing methods

obj.defaultMethod();

obj.protectedMethod();

obj.publicMethod();

}

}

Summary

  • Abstract Class: Used when you want to provide a common interface for subclasses while leaving some methods to be implemented by them.

  • Interface: Used when you want to provide a contract that implementing classes must adhere to, allowing multiple inheritance.

  • Access Control: Determines the accessibility of classes, methods, and variables, ensuring encapsulation and security in Java programs.

3.13 Packages

In Java, packages are used to organize classes into namespaces, providing a way to modularize code and prevent naming conflicts. A package can contain multiple classes and sub-packages, helping to maintain code organization and structure.

3.13.1 Packages Concept

Key Points:

  • Namespace: Packages provide a way to create separate namespaces for classes, preventing naming conflicts.

  • Organization: Packages help organize related classes and resources.

  • Access Control: Classes in the same package can access each other's package-private members directly.

  • Naming Convention: Package names are usually in lowercase and follow a reverse domain name convention (e.g., com.example.package).

3.13.2 Creating User-defined Packages

Package Declaration

To declare a class to be a part of a package, use the package keyword followed by the package name at the top of the source file.

package com.example.mypackage;


public class MyClass {

// Class members and methods

}

Using User-defined Packages

To use a class from a user-defined package, you can either specify the fully qualified class name or import the package.

Example:

import com.example.mypackage.MyClass;


public class Main {

public static void main(String[] args) {

MyClass obj = new MyClass();

// Use obj

}

}

3.13.3 Java Built-in Packages

Java provides several built-in packages that contain a variety of classes and interfaces for different functionalities.

Examples of Built-in Packages:

  • java.lang: Contains fundamental classes and interfaces that are automatically imported into every Java program.

  • java.util: Contains utility classes and interfaces, such as collections framework, date and time utilities, etc.

  • java.io: Contains classes for handling input and output operations, such as file I/O, streams, etc.

  • java.net: Contains classes for networking operations, such as sockets, URLs, etc.

3.13.4 Import Statement, Static Import

Import Statement

The import statement is used in Java to make classes and interfaces from other packages available in the current source file.

Example:

import java.util.ArrayList;

import java.util.List;

Static Import

The static import statement is used to import static members (fields and methods) of a class or interface so that they can be used directly without qualification.

Example:

import static java.lang.Math.PI;

Summary

  • Packages: Used for organizing classes and resources into namespaces, preventing naming conflicts and providing modularity.

  • User-defined Packages: Created by using the package keyword in source files and can be imported for use in other classes.

  • Built-in Packages: Provided by Java and contain classes and interfaces for various functionalities.

  • Import Statement: Used to import classes and interfaces from other packages.

  • Static Import: Used to import static members of a class or interface for direct use without qualification.

3.14 Collection

In Java, the Collection Framework provides a set of classes and interfaces to represent and manipulate collections of objects. Collections are used to store, retrieve, and manipulate groups of objects.

3.14.1 Collection Framework

The Collection Framework in Java provides a unified architecture for representing and manipulating collections of objects. It includes interfaces, implementations, and algorithms to work with collections.

Key Components:

  • Interfaces: Defines contracts for different types of collections.

  • Implementations: Provides concrete implementations of the collection interfaces.

  • Algorithms: Contains algorithms to operate on collections.

3.14.2 Interfaces: Collection, List, Set

Collection Interface

  • Represents a group of objects known as elements.

  • Does not guarantee any specific order of elements.

  • Key Subinterfaces: List, Set.

List Interface

  • Represents an ordered collection (sequence) of elements.

  • Allows duplicate elements.

  • Key Implementations: ArrayList, LinkedList.

Set Interface

  • Represents a collection of unique elements.

  • Does not allow duplicate elements.

  • Key Implementations: HashSet, TreeSet.

3.14.3 Navigation: Enumeration, Iterator, ListIterator

Enumeration Interface

  • Allows iterating through elements of a collection.

  • Only supports read operations.

  • Superseded by Iterator interface.

Iterator Interface

  • Allows traversing through elements of a collection.

  • Supports both read and remove operations.

  • More flexible and powerful than Enumeration.

ListIterator Interface

  • Extends Iterator interface and allows bidirectional traversal of elements in a list.

  • Supports additional operations like adding and modifying elements during traversal.

3.14.4 Classes: LinkedList, ArrayList, Vector, HashSet

LinkedList Class

  • Implements the List interface using a doubly linked list.

  • Provides efficient insertion and deletion operations.

  • Suitable for frequent insertion and deletion operations.

ArrayList Class

  • Implements the List interface using a dynamic array.

  • Provides fast random access to elements.

  • Suitable for scenarios requiring frequent access to elements by index.

Vector Class

  • Deprecated since Java 2, replaced by ArrayList.

  • Similar to ArrayList but synchronized (thread-safe).

  • Slower than ArrayList due to synchronization overhead.

HashSet Class

  • Implements the Set interface using a hash table.

  • Does not guarantee the order of elements.

  • Provides constant-time performance for basic operations (add, remove, contains) on average.

Summary

  • Collection Framework: Provides a unified architecture for representing and manipulating collections of objects.

  • Interfaces: Collection, List, and Set define contracts for different types of collections.

  • Navigation: Enumeration, Iterator, and ListIterator allow traversing through elements of collections.

  • Classes: LinkedList, ArrayList, Vector, and HashSet are commonly used implementations of collection interfaces.



No comments:

Post a Comment