[java basic syntax] explain the Lambda expression of Java in detail

Posted by hammadtariq on Tue, 21 Dec 2021 15:09:44 +0100

1. Introduction

  • Lambda expressions are an important new feature in Java se 8
  • Lambda expressions allow you to use expressions instead of functional interfaces
  • Lambda expressions, like methods, provide a list of normal parameters and a body that uses these parameters
  • Lambda expression can be regarded as an anonymous function based on λ The name of calculus can also be called closure
  • Lambda expressions allow functions to be used as arguments to a method

2. Syntax of lambda expression

Basic form: Lambda expression consists of three parts: parameter, - > symbol and method body

(parameter list)->{Method body}

Supplement:

  • Lambda expressions can have zero or more arguments
  • The type of the parameter can be explicitly declared or not declared, which is implicitly inferred by the JVM. For example, (int a) and (a) have the same effect
  • When there is only one parameter and the type can be deduced, parentheses can be omitted. For example, the effect of (a) is the same as that of A
  • If the method body of a Lambda expression has only one statement, curly braces can be omitted
  • If the method body of a Lambda expression has only one statement and is a return value, return can be omitted

Code example:

// No parameters are required, and the return value is 2
()->2
    
// Receive a parameter (numeric type) and return a value twice its value
x->2*x

// Receives two parameters (numeric type) and returns their sum
(x,y)->x+y
    
// Receives two int type parameters and returns their product
(int x,int y)->x*y

// Receive a String object and print it on the console
(String s)->System.out.println(s)

3. Function interface

If there is only one abstract method in an interface, such an interface is called a single interface. Starting with JDK8, Java uses Lambda expressions and calls a single interface a function interface

be careful:

  • If an interface has only one abstract method, the interface is a functional interface
  • If we declare @ FunctionInterface annotation on an interface, the compiler will require the interface according to the definition of functional interface. Therefore, this interface can only have one abstract method. If it exceeds, the program will report an error when compiling

Example code:

@functionInterface
interface A{
    void test();
}

4. Use of lamdba expression

Next, we will demonstrate the use of Lambda expressions

// No return value no parameter 
@FunctionalInterface interface NoParameterNoReturn { void test(); }
// No return value a parameter 
@FunctionalInterface interface OneParameterNoReturn { void test(int a); }
// Multiple parameters without return value 
@FunctionalInterface interface MoreParameterNoReturn { void test(int a,int b); }
// Return value without parameter 
@FunctionalInterface interface NoParameterReturn { int test(); }
// There is a parameter with a return value 
@FunctionalInterface interface OneParameterReturn { int test(int a); }
// Multiple parameters with return value 
@FunctionalInterface interface MoreParameterReturn { int test(int a,int b); }

public class TestDemo { 
    public static void main(String[] args) { 
        NoParameterNoReturn noParameterNoReturn = ()->{ System.out.println("No parameter no return value"); };
        noParameterNoReturn.test(); 
        
        OneParameterNoReturn oneParameterNoReturn = (int a)->{ System.out.println("No parameter, one return value:"+ a); };
        oneParameterNoReturn.test(10); 
        
        MoreParameterNoReturn moreParameterNoReturn = (int a,int b)->{ System.out.println("Multiple parameters without return value:"+a+" "+b); };
        moreParameterNoReturn.test(20,30); 
        
        NoParameterReturn noParameterReturn = ()->{ System.out.println("Return value, no parameter!"); return 40; };
        //The return value of the receive function 
        int ret = noParameterReturn.test(); 
        System.out.println(ret); 
        
        OneParameterReturn oneParameterReturn = (int a)->{ System.out.println("There are return values and parameters!"); return a; };
        ret = oneParameterReturn.test(50); 
        System.out.println(ret); 
        
        MoreParameterReturn moreParameterReturn = (int a,int b)->{ System.out.println("Multiple parameters with return value!"); return a+b; };
        ret = moreParameterReturn.test(60,70);
		System.out.println(ret); 
    } 
}

5. Variable capture

5.1 introduction

Variable capture exists in both local and anonymous classes in Java

Only after we understand what is variable capture can we better understand the scope of Lambda expressions, because Lambda expressions also have variable capture.

5.2 variable capture of anonymous inner class

class A { 
    public void func(){ 
        System.out.println("func()"); 
    } 
}
public class TestDemo { 
    public static void main(String[] args) { 
        int a = 100; 
        new Test(){ 
            @Override public void func() { 
                System.out.println("I am an inner class and override it func This method!");
                System.out.println("I'm capturing variables a == "+a +" I am a constant, or a variable that has not changed its value!"); 
            } 
        }; 
    } 
}

The variable a in the above code is the capture variable. This variable is either modified by final, or it is necessary to ensure that this variable is not modified when used in the anonymous inner class. If it is modified, there will be a compilation error

5.3 Lambda's variable capture

Variable capture can also be performed in Lambda

@FunctionalInterface interface A { 
    void test(); 
}
public static void main(String[] args) { 
    int a = 10; 
    NoParameterNoReturn noParameterNoReturn = ()->{
        // a = 99;  If a is modified, an error will be reported 
        System.out.println("Capture variables:"+a); 
    };
    noParameterNoReturn.test(); 
}

6. Use of lambda in collection

In order to better use Lambda and Java collection classes together, some interfaces are added to the collection to connect with Lambda expressions

Corresponding interfaceNew method
CollectionremoveIf(),spliterator(),stream(),parallelStream(),forEach()
ListreplaceAll(),sort()
MapgetDefault(),forEach(),replaceAll(),putIfAbsent(),remove(),replace(),computeIfAbsent(),computeIfPresent(),compute(),merge()

Supplement:

The forEach() method of the Collection is from the Java. Net interface Inherited from lang. interoperable

6.1 Collection interface

Use the forEach() method for demonstration

forEach() source code:

Code example: using anonymous inner classes

public class TestDemo{
    public static void main(String[] args) {
        List<String> list=new ArrayList<>();
        list.add("aaa");
        list.add("bbb");
        list.add("ccc");
        list.forEach(new Consumer<String>() {
            @Override
            public void accept(String s) {
                System.out.print(s+" ");
            }
        });
    }
}
// The result was aaa bbb ccc

Code example: using Lambda

public class TestDemo{
    public static void main(String[] args) {
        List<String> list=new ArrayList<>();
        list.add("aaa");
        list.add("bbb");
        list.add("ccc");
        list.forEach(s -> System.out.print(s+" "));
    }
}
// The result was aaa bbb ccc

6.2 List interface

Use the sort() method for demonstration

sort() source code:

Code example: using anonymous inner classes

public class TestDemo{
    public static void main(String[] args) {
        List<String> list=new ArrayList<>();
        list.add("aaa");
        list.add("bbb");
        list.add("ccc");
        list.sort(new Comparator<String>() {
            @Override
            public int compare(String o1, String o2) {
                return o1.compareTo(o2);
            }
        });
        System.out.println(list);
    }
}
// The result is: [aaa, bbb, ccc]

Code example: using Lambda

public class TestDemo{
    public static void main(String[] args) {
        List<String> list=new ArrayList<>();
        list.add("aaa");
        list.add("bbb");
        list.add("ccc");
        list.sort((String o1,String o2)->o1.compareTo(o2));
        System.out.println(list);
    }
}
// The result is: [aaa, bbb, ccc]

6.3 Map interface

Demonstrate using the forEach() method of HashMap

The forEach() source code of HashMap:

Code example: using anonymous inner classes

public class TestDemo{
    public static void main(String[] args) {
        Map<Integer,String> map=new HashMap<>();
        map.put(1,"aaa");
        map.put(2,"222");
        map.put(3,"333");
        map.forEach(new BiConsumer<Integer, String>() {
            @Override
            public void accept(Integer integer, String s) {
                System.out.println("Key="+integer+" Value="+s);
            }
        });
    }
}
/** The result is:
Key=1 Value=aaa
Key=2 Value=222
Key=3 Value=333
*/

Code example: using Lambda

public class TestDemo{
    public static void main(String[] args) {
        Map<Integer,String> map=new HashMap<>();
        map.put(1,"aaa");
        map.put(2,"222");
        map.put(3,"333");
        map.forEach((Integer integer,String s)->
                System.out.println("Key="+integer+" Value="+s));
    }
}
/** The result is:
Key=1 Value=aaa
Key=2 Value=222
Key=3 Value=333
*/

7. Advantages and disadvantages of lambda expression

advantage:

  • Simple code and rapid development
  • Convenient functional programming
  • Easy parallel computing
  • Java introduces Lambda to improve collection operation

Disadvantages:

  • Poor code readability
  • In non parallel computing, many calculations may not have the high performance of the traditional for loop

Topics: Java Back-end JavaSE