Home  >  Article  >  Java  >  What are the methods used in Lambda expressions in Java

What are the methods used in Lambda expressions in Java

WBOY
WBOYforward
2023-06-03 16:55:541136browse

    1. Introduction to Lambda expressions

    Lambda expression (closure): a new feature of java8, lambda runs a function as a parameter of a method , that is, the function is passed into the method as a parameter. Using lambda expressions can make your code more concise.

    Usage scenarios of Lambda expressions: used to simplify interface implementation.

    Regarding interface implementation, there are many ways to implement it. For example: design the implementation class of the interface and use anonymous inner classes. But lambda expressions are simpler than both of these methods.

    package test;
    /**
     * @author: Mercury
     * Date: 2022/3/20
     * Time: 17:48
     * Description:Lambda表达式
     * Version:1.0
     */
    public class Test04 {
        public static void main(String[] args) {
            //使用lambda表达式实现接口
            Test test = () -> {
                System.out.println("test");
            };
            test.test();
        }
    }
    interface Test{
        public void test();
    }

    2. Requirements of Lambda expressions on interfaces

    Although lambda expressions can simplify the implementation of interfaces to a certain extent. However, not all interfaces can be implemented concisely using lambda expressions.

    The lambda expression is just an anonymous method after all. Lambda expressions are not applicable when there are too many or too many methods in the implemented interface.

    Lambda expressions can only implement functional interfaces.

    1. Functional interface

    If we say that in an interface, there is only one abstract method that the implementing class must implement! Such an interface is a functional interface.

    The code is as follows (example):

    //有且只有一个实现类必须要实现的抽象方法,所以是函数式接口
    interface Test{
        public void test();
    }

    2.@FunctionalInterface

    is an annotation, used before the interface to determine whether the interface is ⼼A functional interface. If it is a functional interface, there is no problem. If it is not a functional interface, an error will be reported. Function similar to @Override.
    The code is as follows (example):

    @FunctionalInterface
    interface Test{
        public void test();
    }

    3. The syntax of Lambda expression

    1. The basic syntax of Lambda expression

    lambda expression, in fact, the essence In other words, it is an anonymous function. Therefore, when writing lambda expressions, you do not need to care about the method name.

    In fact, when we write lambda expressions, we don’t need to care about the return value type.

    When we write lambda expressions, we only need to pay attention to two parts: parameter list and method body

    Basic syntax of lambda expressions:
    (parameter 1, parameter 2,…) -> {
    Method body
    };

    Parameter part: The parameter list of the method, which must be consistent with the method parameter part in the implemented interface, including the number of parameters and type.

    Method body part: The implementation part of the method. If the method defined in the interface has a return value, pay attention to the return value when implementing it.

    -> : Separates the parameter part and the method body part.

    Code example:

    package test;
    /**
     * @author: Mercury
     * Date: 2022/3/20
     * Time: 17:48
     * Description:Lambda表达式
     * Version:1.0
     */
    public class Test04 {
        public static void main(String[] args) {
            //使用lambda表达式实现接口
            //无参
    //        Test test = () -> {
    //            System.out.println("test");
    //        };
            //有参
    //        Test test = (name,age) -> {
    //            System.out.println(name+age+"岁了!");
    //        };
    //        test.test("小新",18);
            //有参+返回值
            Test test = (name,age)  -> {
                System.out.println(name+age+"岁了!");
                return age + 1;
            };
            int age = test.test("小新",18);
            System.out.println(age);
        }
    }
    //无参
    //interface Test{
    //    public void test();
    //}
    //有参 无返回值
    //interface Test{
    //    public void test(String name,int age);
    //}
    //有参 有返回值
    interface Test{
        public int test(String name,int age);
    }

    4. Syntax advancement of Lambda expression

    Simplification of parameter part

    Type of parameter

    Because in the interface method, the type of each parameter has been defined. And when using lambda expressions to implement interfaces, you must ensure that the number and type of parameters are consistent with the methods in the interface. Therefore, the type of parameters in the lambda expression can be omitted at this time.

    Note:

    If you need to omit the parameter type, make sure: If you want to omit it, the type of each parameter must be omitted and not written. It must not appear. Some parameter types are omitted, and some parameter types are not omitted.

            //有参+返回值
            Test test = (name,age)  -> {
                System.out.println(name+age+"岁了!");
                return age + 1;
            };
            int age = test.test("小新",18);
            System.out.println(age);

    Parents for parameters

    If there is and is only one parameter in the parameter list of a method, at this time, the parentheses of the parameter list can be omitted. written.

    Note:

    • Only when the number of parameters is one, more or less parameters cannot be omitted.

    • When omitting the parentheses, the type of the parameter must be omitted

            //一个参数
            Test test = name -> {
                System.out.println(name+"test");
            };
            test.test("小新");

    Simplification of the method body

    Simplification of braces in method body

    When the logic in a method body has one and only one sentence, the braces can be omitted

    Test test = name -> System.out.println(name+"test");
            test.test("小新");

    return Simplification

    If the only statement in a method is a return statement, when omitting the curly brackets, the return must also be omitted.

    Test test = (a,b) -> a+b;

    3. Function reference

    Lambda expression is to simplify the implementation of the interface. In lambda expressions, more complex logic should not appear. The use of overly complex logic in lambda expressions will greatly affect the readability of the program. Normally, if a lambda expression needs to handle complex logic, we will write a separate method to handle it. Just reference this method directly in the lambda expression.

    Function reference: Reference an existing method to replace the lambda expression to complete the interface implementation

    1. Reference to static method

    Syntax: Class::Static Method

    Note:

    • After the referenced method, do not add small brackets.

    • The referenced method, parameters (number, type) and return value must be consistent with those defined in the interface

    package test;
    /**
     * @author: Mercury
     * Date: 2022/3/20
     * Time: 18:17
     * Description:lambda表达式静态方法引用
     * Version:1.0
     */
    public class Test05 {
        public static void main(String[] args) {
            //实现多个参数,一个返回值的接口
            //对一个静态方法的引用,语法:类::静态方法
            Test1 test1 = Calculator::calculate;
            System.out.println(test1.test(4,5));
        }
    }
    class Calculator{
        public static int calculate(int a,int b ){
            // 稍微复杂的逻辑:计算a和b的差值的绝对值
            if (a > b) {
                return a - b;
            }
            return b - a;
        }
    }
    interface Test1{
        int test(int a,int b);
    }
    package test;
    /**
     * @author: Mercury
     * Date: 2022/3/20
     * Time: 18:17
     * Description:lambda表达式静态方法引用
     * Version:1.0
     */
    public class Test05 {
        public static void main(String[] args) {
            //实现多个参数,一个返回值的接口
            //对一个静态方法的引用,语法:类::静态方法
            Test1 test1 = Calculator::calculate;
            System.out.println(test1.test(4,5));
        }
    }
    class Calculator{
        public static int calculate(int a,int b ){
            // 稍微复杂的逻辑:计算a和b的差值的绝对值
            if (a > b) {
                return a - b;
            }
            return b - a;
        }
    }
    interface Test1{
        int test(int a,int b);
    }

    2 .Reference of non-static method

    Syntax: Object::Non-static method

    Notes:

    • Do not add parentheses after the quoted method.

    • 引用的这个方法, 参数(数量、类型) 和 返回值, 必须要跟接口中定义的⼀致。

    package test;
    /**
     * @author: Mercury
     * Date: 2022/3/21
     * Time: 8:14
     * Description:lambda表达式对非静态方法的引用
     * Version:1.0
     */
    public class Test06 {
        public static void main(String[] args) {
            //对非静态方法的引用,需要使用对象来完成
            Test2 test2 = new Calculator()::calculate;
            System.out.println(test2.calculate(2, 3));
        }
        private static class Calculator{
            public int calculate(int a, int b) {
                return a > b ? a - b : b - a;
             }
        }
    }
    interface Test2{
        int calculate(int a,int b);
    }

    3.构造方法的引用

    使用场景

    如果某个函数式接口中所定义的方法只是为了获取一个类的对象。此时我们就可以使用构造方法的引用,简化这个方法的实现。

    语法:类名::new

    注意事项:可以通过接口中的方法的参数, 区分引用不同的构造方法。

    package com.cq.test;
    /**
     * @author: Mercury
     * Date: 2022/4/27
     * Time: 10:31
     * Description:lambda构造方法的引用
     * Version:1.0
     */
    public class Test {
        private static class Dog{
            String name;
            int age;
            //无参构造
            public Dog(){
                System.out.println("一个Dog对象通过无参构造被实例化了");
            }
            //有参构造
            public Dog(String name,int age){
                System.out.println("一个Dog对象通过有参构造被实例化了");
                this.name = name;
                this.age = age;
            }
        }
        //定义一个函数式接口,用以获取无参的对象
        @FunctionalInterface
        private interface GetDog{
            //若此方法仅仅是为了获得一个Dog对象,而且通过无参构造去获取一个Dog对象作为返回值
            Dog test();
        }
        //定义一个函数式接口,用以获取有参的对象
        @FunctionalInterface
        private interface GetDogWithParameter{
            //若此方法仅仅是为了获得一个Dog对象,而且通过有参构造去获取一个Dog对象作为返回值
            Dog test(String name,int age);
        }
        // 测试
        public static void main(String[] args) {
            //lambda表达式实现接口
            GetDog lm = Dog::new; //引用到Dog类中的无参构造方法,获取到一个Dog对象
            Dog dog = lm.test();
            System.out.println("修狗的名字:"+dog.name+" 修狗的年龄:"+dog.age); //修狗的名字:null 修狗的年龄:0
            GetDogWithParameter lm2 = Dog::new;//引用到Dog类中的有参构造,来获取一个Dog对象
            Dog dog1 = lm2.test("萨摩耶",2);
            System.out.println("修狗的名字:"+dog1.name+" 修狗的年龄:"+dog1.age);//修狗的名字:萨摩耶 修狗的年龄:2
        }
    }

    四、Lambda表达式需要注意的问题

    这⾥类似于局部内部类、匿名内部类,依然存在闭包的问题。

    如果在lambda表达式中引用了局部变量,则该局部变量会隐式声明为final变量。是⼀个常量,不能修改值。

    The above is the detailed content of What are the methods used in Lambda expressions in Java. For more information, please follow other related articles on the PHP Chinese website!

    Statement:
    This article is reproduced at:yisu.com. If there is any infringement, please contact admin@php.cn delete