Difference between Anonymous Inner Class and Lambda Expression

An anonymous inner class is a class that is defined inline without giving it a name. It’s typically used for creating a single-use class that implements an interface or extends a class. Anonymous inner classes are often employed when you need to provide the implementation for a specific interface or class without the need to define a separate named class.

Uses:- Anonymous inner classes are useful when you need a quick, one-time implementation of an interface or a subclass without creating a separate named class. However, they are limited to providing implementations and can’t have their own constructors or additional methods beyond what’s inherited.

Note – Anonymous inner classes can extend a normal class, or abstract class and also can implement an interface that contains any number of methods. The lambda expression can implement an interface that contains a single abstract method.

Example of using an anonymous inner class to implement an interface.

interface Greeting {
    void greet();
}

public class AnonymousInnerClassExample {
    public static void main(String[] args) {
        // Creating an instance of the Greeting interface using an anonymous inner class
        Greeting englishGreeting = new Greeting() {
            @Override
            public void greet() {
                System.out.println("Hello!");
            }
        };

        // Calling the greet() method of the anonymous inner class
        englishGreeting.greet();
    }
}

Output:-

Hello!

In this example, we define an interface Greeting with a single method greet(). Then, in the main method of the AnonymousInnerClassExample class, we create an instance of the Greeting interface using an anonymous inner class. The anonymous inner class provides the implementation for the greet() method by overriding it with the desired behavior.

Example of an anonymous inner class to using an existing class

class Parent {
    void display() {
        System.out.println("This is the parent class.");
    }
}

public class AnonymousInnerClassExample {
    public static void main(String[] args) {
        // Creating an instance of the Parent class using an anonymous inner class
        Parent child = new Parent() {
            @Override
            void display() {
                System.out.println("This is the anonymous child class.");
            }
        };

        // Calling the overridden display() method of the anonymous inner class
        child.display();
    }
}

Output:-

This is the anonymous child class.

In the first example, the anonymous inner class implements the Greeting interface and provides a custom implementation for the greet() method, printing “Hello!” when the englishGreeting.greet() method is called.

In the second example, the anonymous inner class extends the Parent class and overrides the display() method. When the child.display() method is called, it prints “This is the anonymous child class.” instead of the default message from the Parent class.

Java 8 lambda expressions

Java 8 introduced lambda expressions, which are a concise way to represent anonymous functions. They are particularly useful for providing implementations of functional interfaces, which are interfaces with a single abstract method (also known as functional interfaces). Lambda expressions improve the readability and maintainability of code, especially when working with collections, streams, and other functional programming constructs.

Example of using lambda expressions

interface Operation {
    int perform(int a, int b);
}

public class LambdaExpressionExample {
    public static void main(String[] args) {
        // Using a lambda expression to implement the Operation interface
        Operation addition = (a, b) -> a + b;
        Operation subtraction = (a, b) -> a - b;
        Operation multiplication = (a, b) -> a * b;

        // Using the lambda expressions to perform operations
        System.out.println("Addition: " + addition.perform(5, 3));
        System.out.println("Subtraction: " + subtraction.perform(8, 4));
        System.out.println("Multiplication: " + multiplication.perform(6, 2));
    }
}

Output:-

Addition: 8
Subtraction: 4
Multiplication: 12

In this example, we define a functional interface Operation with a single abstract method perform(int a, int b). Then, we use lambda expressions to provide implementations for this interface. The lambda expressions (a, b) -> a + b, (a, b) -> a - b, and (a, b) -> a * b represent different operations: addition, subtraction, and multiplication.

Lambda expressions are used to create instances of functional interfaces. In the main method, we create instances of the Operation interface using lambda expressions and then call the perform method on those instances to perform the respective operations.

Lambda expressions are a powerful feature in Java 8 and later versions, enabling more concise and expressive code when working with functional programming paradigms.

Difference between Anonymous Inner Class and Lambda Expression

Let’s see the comparison between Anonymous Inner Classes and Lambda Expressions in Java:

AspectAnonymous Inner ClassLambda Expression
SyntaxMore verbose syntax, requires class definition.Concise syntax, no need to define a new class.
Functional InterfaceCan be used with both functional and non-functional interfaces.Primarily used with functional interfaces.
Interface/Functional MethodAn anonymous inner class can have multiple methods.Lambda expression is limited to single-method interfaces (functional interfaces).
Code LengthTends to be longer due to class declaration and method implementation.Shorter due to its concise syntax.
ReadabilityCan be less readable, especially for simple operations.Generally more readable, especially for simple operations.
ScopeCan access instance variables and outer class methods.Can access effectively final variables (local variables and instance variables).
PerformanceCan potentially have a slight performance overhead due to object creation.Generally performs better due to lightweight implementation.
SerializationSerializable if the outer class is serializable.Not serializable.
Use CasesUseful for more complex implementations and when access to instance members is needed.Suited for short, simple implementations where conciseness is crucial.

It’s important to note that while both Anonymous Inner Classes and Lambda Expressions can achieve similar results in some scenarios, lambda expressions are more suited for functional programming and situations where concise, readable code is desired.

See anonymous inner class docs.

That’s all about the difference between Anonymous Inner Class and Lambda Expression.