码迷,mamicode.com
首页 > 其他好文 > 详细

Lambda表达式

时间:2019-07-24 22:24:57      阅读:122      评论:0      收藏:0      [点我收藏+]

标签:内部类   面向对象的思想   匿名   print   package   tree   区别   ati   接口   

#java8——Lambda表达式

1.简介:

jdk1.8中引入Lambda表达式,其作用是使用它设计的代码会更加简洁。当开发者在编写Lambda表达式时,也会随之被编译成一个函数式接口。下面这个例子就是使用Lambda语法来代替匿名的内部类,代码不仅简洁,而且还可读。

eg:摘自百度百科:
没有使用Lambda的老方法:

button.addActionListener(new ActionListener(){
    public void actionPerformed(ActionEvent actionEvent){
        System.out.println("Action detected");
    }
});

使用lambda后:

button.addActionListener( actionEvent -> { 
    System.out.println("Action detected");
});

Lambda表达式中,在Thread多线程的使用过程中较为频繁:如:
使用匿名内部类的时候重写run方法:

Runnable runnable1=new Runnable(){
@Override
public void run(){
    System.out.println("Running without Lambda");
}
};

使用Lambda后:

Runnable runnable2=()->System.out.println("Running from Lambda");

lambda表达式的标准格式:
  有三部分
  一些参数
   一个箭头
   一段代码
  格式:
       (参数列表)->{一些重写方法的代码}
       解释说明格式:
   ()接口中抽象方法的参数列表:没有参数空,有就写,多个用,分割
   ->传递的意思,把参数传递给方法体{}
   {}重写接口的抽象方法的方法体

2,函数式编程思想概述

2.1 区别:
面向对象的思想:    
    ·做一件事情,找一个能解决这个事情的对象,调用对象的方法,完成事情.
函数式编程思想:
    ·只要能获取到结果,谁去做的,怎么做的都不重要,重视的是结果,不重视过程

3. 讲述

例如:在多线程中:创建一个实现类,用于实现RUnnable接口,重写了run方法

public class RunnableImpl implements Runnable {
    @Override
    public void run() {
        System.out.println(Thread.currentThread().getName()+"新的线程创建了---");
    }
}
创建主类,用于实现
public class Demo1Runnable {
    public static void main(String[] args) {
        RunnableImpl runnable=new RunnableImpl();
        Thread t=new Thread(runnable);
        t.start();
        //简化代码,匿名内部类
       Runnable runnable1= new Runnable(){

            @Override
            public void run() {
                System.out.println(Thread.currentThread().getName()+"新的线程创建了---");
            }
        };
        new Thread(runnable1).start();//调用线程的启动。
}

这是存在冗余的程序代码块,

简化一:
public class Demo1Runnable {
    public static void main(String[] args) {
        RunnableImpl runnable=new RunnableImpl();
        Thread t=new Thread(runnable);
        t.start();
        //简化代码,匿名内部类
       Runnable runnable1= new Runnable(){

            @Override
            public void run() {
                System.out.println(Thread.currentThread().getName()+"新的线程创建了---");
            }
        };
       new Thread(runnable1).start();
       //继续简化
        new Thread(new Runnable(){

            @Override
            public void run() {
                System.out.println(Thread.currentThread().getName()+"新的线程创建了---");
            }
        }).start();
    }

}
采用匿名内部类,实现线程。

总结:

简化该线程的方法:
1. 
     Runnable runnable1= new Runnable(){

            @Override
            public void run() {
                System.out.println(Thread.currentThread().getName()+"新的线程创建了---");
            }
        };
       new Thread(runnable1).start();

2.  这段代码是1中的综合
     new Thread(new Runnable(){

            @Override
            public void run() {
                System.out.println(Thread.currentThread().getName()+"新的线程创建了---");
            }
        }).start();
3. 使用lambda进行简化codes
    lambda表达式的标准格式:
*   有三部分
*   一些参数
*   一个箭头
*   一段代码
*  格式:
*       (参数列表)->{一些重写方法的代码}
*       解释说明格式:
*   ()接口中抽象方法的参数列表:没有参数空,有就写,多个用,分割
*   ->传递的意思,把参数传递给方法体{}
*   {}重写接口的抽象方法的方法体

codes:

    public class Demo02Lambda {
        public static void main(String[] args) {
        //使用匿名内部类的方式实现多线程
        new Thread(new Runnable(){

            @Override
            public void run() {
                System.out.println(Thread.currentThread().getName()+"新的线程创建了---");
            }
        }).start();
        //使用lambda表达式实现多线程
        new Thread(()-> {
                System.out.println(Thread.currentThread().getName()+"新的线程创建了---");
            }
        ) .start();
        //优化省略lambda
        new Thread(()->System.out.println(Thread.currentThread().getName()+"新的线程创建了---")
        ) .start();
        }

    }

案例二(无参无返回值):

给定一个厨子 Cook 接口,内含唯一的抽象方法 makeFood ,且无参数、无返回值。如下:

public interface Cook {
    public abstract void makeFood();
}

在下面的代码中,请使用Lambda的标准格式调用 invokeCook 方法,打印输出“吃饭啦!”字样:
技术图片
解答:

    public class Demo1Cook {
    public static void main(String[] args) {
        invokeCook(new Cook() {
            @Override
            public void makeFood() {
                System.out.println("吃放了");
            }
        });
       // 使用lambda表达式
        invokeCook(()->{
            System.out.println("吃饭了");
        });
        //省略lambda
        invokeCook(()->System.out.println("吃饭了"));
    }
    //定义方法,参数传递cook接口,方法内部调用cook接口中的方法makeFood
    public static void invokeCook(Cook cook){
        cook.makeFood();
    }

    }

案例三(参数和返回值):

需求:
使用数组存储多个Person对象
对数组中的Person对象使用Arrays的sort方法通过年龄进行升序排序
1.创建Person类

package com.lambdaDemo;
public class Person {
    private String name;
    private int age;

    public Person() {
    }

    public Person(String name, int age) {
        this.name = name;
        this.age = age;
    }

    public String getName() {
        return name;
    }

    public void setName(String name) {
        this.name = name;
    }

    public int getAge() {
        return age;
    }

    public void setAge(int age) {
        this.age = age;
    }

    @Override
    public String toString() {
        return "Person{" +
                "name='" + name + '\'' +
                ", age=" + age +
                '}';
    }
}

传统的排序:

import java.util.Arrays;
import java.util.Comparator;
public class Demo06Comparator {
public static void main(String[] args) {
    // 本来年龄乱序的对象数组
    Person[] array = {
    new Person("古力娜扎", 19),
    new Person("迪丽热巴", 18),
    new Person("马尔扎哈", 20) };
    // 匿名内部类
        Comparator<Person> comp = new Comparator<Person>({
                @Override
                public int compare(Person o1, Person o2) {
                return o1.getAge() ‐ o2.getAge();
            }
        };
        Arrays.sort(array, comp); // 第二个参数为排序规则,即   Comparator接口实例
        for (Person person : array) {
            System.out.println(person);
        }
    }
}

知识点:创建对象数组:

对象名[] 数组名称={new 对象名(),new 对象名(),new 对象名(),  }

排序:
使用Comparator

Comparator<Person> comp = new Comparator<Person>({
                @Override
                public int compare(Person o1, Person o2) {
                return o1.getAge() ‐ o2.getAge();
            }
        };
升序是参数1-参数2,降序是参数2-参数1.
记得使用Arrays.sort(array, comp);进行排序,然后遍历数组即可

使用Lambda的排序:

public class Demo1Arrays {
    public static void main(String[] args) {
        Person[] arr={
                new Person("cym",11),
                new Person("yyh",221),
                new Person("jhj",13),
        };
        Arrays.sort(arr, new Comparator<Person>() {
            @Override
            public int compare(Person o1, Person o2) {
                return o1.getAge()-o2.getAge();
            }
        });
        for (Person p : arr) {
            System.out.println(p);
        }
        //使用lambda表达式简化匿名内部类
        System.out.println("------------使用lambda表达式");
        Arrays.sort(arr,(Person o1,Person o2)->{
            return o2.getAge()-o1.getAge();

        });
        Arrays.sort(arr,(o1,o2)->o2.getAge()-o1.getAge());
        for (Person p : arr) {
            System.out.println(p);
        }
    }
}

技术图片

案例三:有参有返回

public interface Calculate {
    //定义两个int和方法
    public abstract int calc(int a,int b);
}

使用lambda

package com.lambdaDemo1;


public class Demo1Calculator {
    public static void main(String[] args) {
        //调用invakeCalc方法,参数是接口,可以使用匿名内部类

        invokeCalc(10, 20, new Calculate() {
            @Override
            public int calc(int a, int b) {
                return  a+b;
            }
        });
        //使用lambda表达式简化匿名内部类的书写
       invokeCalc(10,20,(int a,int b)->{
           return a+b;
       });



       //省略
        invokeCalc(10,20,(a,b)-> a+b);
    }
    //定义一个方法,参数传递两个int类型的整数,参数cdCalculator接口,
    // 方法内部电泳Calculator中的方法calc计算和
    public static void invokeCalc(int a,int b ,Calculate calculate){
        int sum= calculate.calc(a,b);
        System.out.println(sum);
    }
}

Lambda的省略《规则》:

/*可推到可省略
* 凡是根据上下文推到出来的内容,都可以省略书写
* 可以省略的内容:
*   1,(参数列表):括号中参数列表的数据类型,可以省略不写
*   2,(参数列表):括号中的参数如果只有一个,那么类型和()都可以省略
*   3.{代码}ruguo {}的代码只有一行,无论是否有返回值,都可以省略{}return 和分号
*   ·要省略都一起省略

1.  省略前:
    new Thread(()-> {
            System.out.println(Thread.currentThread().getName()+"新的线程创建了---");
        }
    ) .start();
    省略后:
    new Thread(()->System.out.println(Thread.currentThread().getName()+"新的线程创建了---")
    ) .start();
explanation:如果{代码块}中只有一行代码,则可以省去{},和;
2. 省略前:
     invokeCook(()->{
        System.out.println("吃饭了");
    });
    省略后:
    invokeCook(()->System.out.println("吃饭了"));
    explanation:省略了{}和; 因为代码块就一句;
3. 省略前:
     Arrays.sort(arr,(Person o1,Person o2)->{
        return o2.getAge()-o1.getAge();});
    省略后:
    Arrays.sort(arr,(o1,o2)->o2.getAge()-o1.getAge());
    explanation:变量名一样可以省略,代码块就一句话,可以省略return和{} ;
4.  省略前:
    invokeCalc(10,20,(int a,int b)->{
       return a+b;
   });
    省略后:
    invokeCalc(10,20,(a,b)-> a+b);
    explanation:同上

github-----》》》"lambda"

Lambda表达式

标签:内部类   面向对象的思想   匿名   print   package   tree   区别   ati   接口   

原文地址:https://www.cnblogs.com/chenyameng/p/11241150.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!