目录
1.Lambda表达式
1.1 概念
1.2 语法
1.3 代码分析
1.3.1 无参无返回值
1.3.2 有参有返回值
1.3.3 lambda表达式注意事项
2.函数式接口
2.1 内置函数式接口
2.2 Consumer
2.3 Supplier供给型函数式接口
2.4 Function 函数型函数式接口,r>
2.5 Predicated
3.方法引用
3.1 什么是方法引用
3.2 对象::实例方法
3.3 类名::静态方法
3.4 类名::实例方法
3.5 类名::new 引用类的构造器
3.6 类型[]::new
1.Lambda表达式
1.1 概念
(1)Lambda表达式:特殊的匿名内部类,语法更简洁。
(2)Lambda表达式允许把函数作为一个方法的参数(函数作为方法参数传递),将代码像数据一样传递。
1.2 语法
基本语法
<函数式接口> <变量名>=(参数1,参数2...)->{
//方法体
};
注意: 函数式接口:接口中只有一个抽象方法。
(参数1,参数2): 抽象方法的参数
->: 分隔符
{}:表示抽象方法的实现
1.3 代码分析
-
Thread 类需要 Runnable 接口作为参数,其中的抽象 run 方法是用来指定线程任务内容的核心
-
为了指定 run 的方法体,不得不需要 Runnable 接口的实现类
-
为了省去定义一个 Runnable 实现类的麻烦,不得不使用匿名内部类
-
必须覆盖重写抽象 run 方法,所以方法名称、方法参数、方法返回值不得不再写一遍,且不能写错
-
而实际上,似乎只有方法体才是关键所在。
Thread 类需要 Runnable 接口作为参数,其中的抽象 run 方法是用来指定线程任务内容的核心
为了指定 run 的方法体,不得不需要 Runnable 接口的实现类
为了省去定义一个 Runnable 实现类的麻烦,不得不使用匿名内部类
必须覆盖重写抽象 run 方法,所以方法名称、方法参数、方法返回值不得不再写一遍,且不能写错
而实际上,似乎只有方法体才是关键所在。
这时可以使用lambda表示完成上面的要求。
前提:必须是函数式接口。
简化匿名内部类的使用,语法更加简单。
总代码展示:
public class LambdaTest {
public static void main(String[] args) {
My m=new My();
Thread t1=new Thread(m);
t1.start();
Thread t2=new Thread(new Runnable() {
@Override
public void run() {
System.out.println("匿名函数式");
}
});
t2.start();
Runnable t3=()->{
System.out.println("lambda表达式");
};
Thread t03=new Thread(t3);
t03.start();
Thread t4=new Thread(()->{
System.out.println("lambda精简表达式");
});
t4.start();
}
}
class My implements Runnable{
@Override
public void run() {
System.out.println("Runnable方法");
}
}
1.3.1 无参无返回值
代码展示:
public class WuCanWuFan {
public static void main(String[] args) {
Swimming swimming=new Swimming() {
@Override
public void swim() {
System.out.println("小明在游泳");
}
};
fun(swimming);
System.out.println("================lambda=========================");
// Swimming swimming1=()->{
// System.out.println("小花在游泳");
// };
fun(()->{
System.out.println("小花在游泳");
});
}
public static void fun(Swimming swimming){
swimming.swim();
}
}
interface Swimming{
public void swim();
}
1.3.2 有参有返回值
举例演示 java.util.Comparator 接口的使用场景代码,其中的抽象方法定义为:
-
public abstract int compare(T o1, T o2);
当需要对一个对象集合进行排序时, Collections.sort 方法需要一个 Comparator 接口实例来指定排序的规则。
代码展示:
public class Compable {
public static void main(String[] args) {
List people=new ArrayList<>();
people.add(new Person("张三",15,185));
people.add(new Person("李四",23,179));
people.add(new Person("王五",8,145));
people.add(new Person("赵六",34,180));
//对集合中的元素进行排序 按照年龄从小到大
//传统做法:Comparator:排序规则接口
Comparator comparator=new Comparator() {
//int : 0表示新加的元素和集合中的元素是相等的
//1表示新加的元素比集合中的元素大
//-1表示新加的元素比集合中的元素小
@Override
public int compare(Person o1, Person o2) {
return o2.getAge()- o1.getAge();
}
};
Collections.sort(people,comparator);
for (Person p:people) {
System.out.println(p);
}
System.out.println("===============================lambda===============================");
Comparator comparator1=(Person o1,Person o2)->{
return o1.getAge()- o2.getAge();
};
Collections.sort(people,comparator1);
for (Person p:people) {
System.out.println(p);
}
}
}
class Person{
private String name;
private Integer age;
private Integer tall;
public Person() {
}
public Person(String name, Integer age, Integer tall) {
this.name = name;
this.age = age;
this.tall = tall;
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
public Integer getTall() {
return tall;
}
public void setTall(Integer tall) {
this.tall = tall;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + ''' +
", age=" + age +
", tall=" + tall +
'}';
}
}
1.3.3 lambda表达式注意事项
注意事项 :
形参列表的数据类型会自动推断
如果形参列表为空,只需保留()
若形参只有一个,()可以省略,只需要参数的名称即可(此题证明)
如果执行语句只有一句,且无返回值,{}可以省略,若有返回值,则想省去{},则必须同时省略return,且执行语句也保证只有一句
Lambda不会生成一个单独的内部类文件
public class NoticeTest {
public static void main(String[] args) {
fun(n->{
System.out.println(n+"正在玩手机");
});
}
public static void fun(Plays plays){
plays.play("小明");
}
}
interface Plays{
public void play(String name);
}
2.函数式接口
我们知道使用Lambda表达式的前提是需要有函数式接口。而Lambda使用时不关心接口名,抽象方法名,只关心抽 象方法的参数列表和返回值类型。因此为了让我们使用Lambda方便,JDK提供了大量常用的函数式接口。
常见的函数式接口:java.util.function保存
2.1 内置函数式接口
如果一个接口只有一个抽象方法,则该接口称之为函数式接口,函数式接口可以使用Lambda表达式,Lambdda表达式会被匹配到这个抽象方法上。
@Functionallnterface注解检测接口是否符合函数式接口。
public class Test03 {
public static void main(String[] args) {
Operater o=arr -> {
int sum=0;
for(int n:arr){
sum+=n;
}
System.out.println("数组的和为:"+sum);
};
fun(o);
}
public static void fun(Operater operater){
int[] arr={2,3,4,5,6,7,11};
operater.getSum(arr);
}
}
@FunctionalInterface
interface Operater{
//求数组的和
public abstract void getSum(int[] arr);
}
2.2 Consumer
消费型函数 :有参无返回值
举例:去美甲店消费一次的开销
public class ConsumerTest {
public static void main(String[] args) {
Consumer consumer=t->{
System.out.println("美甲花了:"+t);
};
fun(consumer,200);
}
//调用某个方法时,该方法需要的参数为接口类型,这时就应该能想到使用lambda
public static void fun(Consumer consumer, double money){
consumer.accept(money);
}
}
举例:遍历数组和
public class ConsumerTest02 {
public static void main(String[] args) {
getSum(t->{
int sum=0;
for (int i:t) {//此处遍历t即代表arr
sum+=i;
}
System.out.println(sum);
},new int[]{1,2,3,4,5});
}
public static void getSum(Consumer consumer, int[] arr){//注意Consumer
consumer.accept(arr);
}
}
2.3 Supplier供给型函数式接口
T表示返回结果的泛型 :无参有返回值的函数式接口
举例:随机获取0到10之间的数字
public class SupplierTest {
public static void main(String[] args) {
getNumber(()->{
return new Random().nextInt(10);
});
}
public static void getNumber(Supplier supplier){
Integer integer = supplier.get();
System.out.println("获取数字为:"+integer);
}
}
2.4 Function 函数型函数式接口
有参,有返回值
T:参数类型的泛型
R:函数返回结果的泛型
举例:将字符串转大写
public class FunctionTest {
public static void main(String[] args) {
getUpper(t->{
return t.toUpperCase(Locale.ROOT);//所传参数随便写
},"hello world");
}
public static void getUpper(Function function,String str){
String apply = function.apply(str);
System.out.println("结果为:·"+apply);
}
}
举例:计算字符串长度
public class FunctionTest02 {
public static void main(String[] args) {
getLength(t->{
return t.replace(" ","").length();
},"hello world");
}
public static void getLength(Function function,String str){
Integer apply = function.apply(str);
System.out.println("长度为:"+apply);
}
}
2.5 Predicated
boolean test(T t);确定类型为T的对象是否满足条件,并返回boolean类型
举例:判断名字是否过长
public class PredicateTest {
public static void main(String[] args) {
getNameLength(t->{
return t.length()>3?true:false;
},"迪丽热巴.迪力木拉提");
}
public static void getNameLength(Predicate predicate,String name){
boolean test = predicate.test(name);
System.out.println("名字长度是否超过3:"+test);
}
}
3.方法引用
如果我们在Lambda中所指定的功能,已经有其他方法存在相同方案,那是否还有必要再写重复逻辑?可以直接“引 用”过来就好了---方法引用
请注意其中的双冒号 :: 写法,这被称为“方法引用”,是一种新的语法
举例:计算数组和
public class PullIn {
public static void getSum(int[] arr){
int sum=0;
for (Integer i:arr) {
sum+=i;
}
System.out.println("数组和为:"+sum);
}
public static void sum(Consumer consumer){
int[] arr={1, 2, 3, 4, 5};
consumer.accept(arr);
}
public static void main(String[] args) {
//此处与上述getSum方法一模一样,造成冗余
// sum(arr->{
// int sum=0;
// for (Integer i:arr) {
// sum+=i;
// }
// System.out.println("数组和为:"+sum);
// },new int[]{1, 2, 3, 4, 5});
sum(PullIn::getSum);
}
}
3.1 什么是方法引用
方法引用是Lambda表达式的一种简写形式。如果Lambda表达式方法体只是调用一个特定的已经存在的方法,则可以使用方法引用。
常见形式:
(1)对象::方法名
(2)类名::静态方法
(3)类名::普通方法
(4)类名::new 调用的构造器
(5)String[]::new 调用数组的构造器
3.2 对象::实例方法
注意:
1.被引用的方法,参数要和接口中的抽象方法的参数一样
2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
举例:获取当前时间
public class PullInTest01 {
//对象::实例方法
public static void main(String[] args) {
Date d=new Date();
// Supplier time=()->{
// return d.getTime();
// };
//使用方法引用
Supplier time=d::getTime;
//注意:
//1.被引用的方法,参数要和接口中的抽象方法的参数一样
//2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
Long aLong = time.get();
System.out.println("aLong = "+aLong);
}
}
3.3 类名::静态方法
举例:获取当前时间
public class PullInTest02 {
//类名::静态方法
public static void main(String[] args) {
// Supplier su=()->{
// return System.currentTimeMillis();
// };
Supplier su=System::currentTimeMillis;
Long aLong = su.get();
System.out.println("aLong="+aLong);
}
}
3.4 类名::实例方法
(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
举例:字符串长度及截取字符串
public class PullInTest03 {
public static void main(String[] args) {
//类名::实例方法(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
// Function f1=(String str)->{
// return str.length();
// };
Function f1=String::length;
Integer hello = f1.apply("hello");
System.out.println("字符串长度为:"+hello);
//BiFunction f2=String::substring;
//相当于这样的Lambda
BiFunction f2=(String str,Integer index)->{
return str.substring(index);
};
String helloworld = f2.apply("helloworld", 3);
System.out.println(helloworld);
}
}
3.5 类名::new 引用类的构造器
举例:person介绍
Person类
public class Person {
private String name;
private Integer age;
public Person() {
System.out.println("调用无参构造");
}
public Person(String name, Integer age) {
System.out.println("调用有参构造"+name+"---"+age);
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + ''' +
", age=" + age +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
}
测试类
public class PullTest04 {
//类名::new 引用类的构造器
public static void main(String[] args) {
// Supplier su=()->{
// return new Person();
// };
Supplier su=Person::new;
Person person = su.get();
System.out.println(person);
// BiFunction bif=(String name,Integer age)->{
// return new Person(name,age);
// };
BiFunction bif=Person::new;
Person name = bif.apply("小明", 18);
System.out.println(name);
}
}
3.6 类型[]::new
举例:数组存放
public class PullInTest05 {
//类型【】::new
public static void main(String[] args) {
// Function f1=(Integer length)->{
// return new int[length];
// };
Function f1=int[]::new;
int[] apply = f1.apply(10);
System.out.println(Arrays.toString(apply));
}
}
消费型函数 :有参无返回值
举例:去美甲店消费一次的开销
public class ConsumerTest {
public static void main(String[] args) {
Consumer consumer=t->{
System.out.println("美甲花了:"+t);
};
fun(consumer,200);
}
//调用某个方法时,该方法需要的参数为接口类型,这时就应该能想到使用lambda
public static void fun(Consumer consumer, double money){
consumer.accept(money);
}
}
举例:遍历数组和
public class ConsumerTest02 {
public static void main(String[] args) {
getSum(t->{
int sum=0;
for (int i:t) {//此处遍历t即代表arr
sum+=i;
}
System.out.println(sum);
},new int[]{1,2,3,4,5});
}
public static void getSum(Consumer consumer, int[] arr){//注意Consumer
consumer.accept(arr);
}
}
2.3 Supplier供给型函数式接口
T表示返回结果的泛型 :无参有返回值的函数式接口
举例:随机获取0到10之间的数字
public class SupplierTest {
public static void main(String[] args) {
getNumber(()->{
return new Random().nextInt(10);
});
}
public static void getNumber(Supplier supplier){
Integer integer = supplier.get();
System.out.println("获取数字为:"+integer);
}
}
2.4 Function 函数型函数式接口
有参,有返回值
T:参数类型的泛型
R:函数返回结果的泛型
举例:将字符串转大写
public class FunctionTest {
public static void main(String[] args) {
getUpper(t->{
return t.toUpperCase(Locale.ROOT);//所传参数随便写
},"hello world");
}
public static void getUpper(Function function,String str){
String apply = function.apply(str);
System.out.println("结果为:·"+apply);
}
}
举例:计算字符串长度
public class FunctionTest02 {
public static void main(String[] args) {
getLength(t->{
return t.replace(" ","").length();
},"hello world");
}
public static void getLength(Function function,String str){
Integer apply = function.apply(str);
System.out.println("长度为:"+apply);
}
}
2.5 Predicated
boolean test(T t);确定类型为T的对象是否满足条件,并返回boolean类型
举例:判断名字是否过长
public class PredicateTest {
public static void main(String[] args) {
getNameLength(t->{
return t.length()>3?true:false;
},"迪丽热巴.迪力木拉提");
}
public static void getNameLength(Predicate predicate,String name){
boolean test = predicate.test(name);
System.out.println("名字长度是否超过3:"+test);
}
}
3.方法引用
如果我们在Lambda中所指定的功能,已经有其他方法存在相同方案,那是否还有必要再写重复逻辑?可以直接“引 用”过来就好了---方法引用
请注意其中的双冒号 :: 写法,这被称为“方法引用”,是一种新的语法
举例:计算数组和
public class PullIn {
public static void getSum(int[] arr){
int sum=0;
for (Integer i:arr) {
sum+=i;
}
System.out.println("数组和为:"+sum);
}
public static void sum(Consumer consumer){
int[] arr={1, 2, 3, 4, 5};
consumer.accept(arr);
}
public static void main(String[] args) {
//此处与上述getSum方法一模一样,造成冗余
// sum(arr->{
// int sum=0;
// for (Integer i:arr) {
// sum+=i;
// }
// System.out.println("数组和为:"+sum);
// },new int[]{1, 2, 3, 4, 5});
sum(PullIn::getSum);
}
}
3.1 什么是方法引用
方法引用是Lambda表达式的一种简写形式。如果Lambda表达式方法体只是调用一个特定的已经存在的方法,则可以使用方法引用。
常见形式:
(1)对象::方法名
(2)类名::静态方法
(3)类名::普通方法
(4)类名::new 调用的构造器
(5)String[]::new 调用数组的构造器
3.2 对象::实例方法
注意:
1.被引用的方法,参数要和接口中的抽象方法的参数一样
2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
举例:获取当前时间
public class PullInTest01 {
//对象::实例方法
public static void main(String[] args) {
Date d=new Date();
// Supplier time=()->{
// return d.getTime();
// };
//使用方法引用
Supplier time=d::getTime;
//注意:
//1.被引用的方法,参数要和接口中的抽象方法的参数一样
//2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
Long aLong = time.get();
System.out.println("aLong = "+aLong);
}
}
3.3 类名::静态方法
举例:获取当前时间
public class PullInTest02 {
//类名::静态方法
public static void main(String[] args) {
// Supplier su=()->{
// return System.currentTimeMillis();
// };
Supplier su=System::currentTimeMillis;
Long aLong = su.get();
System.out.println("aLong="+aLong);
}
}
3.4 类名::实例方法
(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
举例:字符串长度及截取字符串
public class PullInTest03 {
public static void main(String[] args) {
//类名::实例方法(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
// Function f1=(String str)->{
// return str.length();
// };
Function f1=String::length;
Integer hello = f1.apply("hello");
System.out.println("字符串长度为:"+hello);
//BiFunction f2=String::substring;
//相当于这样的Lambda
BiFunction f2=(String str,Integer index)->{
return str.substring(index);
};
String helloworld = f2.apply("helloworld", 3);
System.out.println(helloworld);
}
}
3.5 类名::new 引用类的构造器
举例:person介绍
Person类
public class Person {
private String name;
private Integer age;
public Person() {
System.out.println("调用无参构造");
}
public Person(String name, Integer age) {
System.out.println("调用有参构造"+name+"---"+age);
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + ''' +
", age=" + age +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
}
测试类
public class PullTest04 {
//类名::new 引用类的构造器
public static void main(String[] args) {
// Supplier su=()->{
// return new Person();
// };
Supplier su=Person::new;
Person person = su.get();
System.out.println(person);
// BiFunction bif=(String name,Integer age)->{
// return new Person(name,age);
// };
BiFunction bif=Person::new;
Person name = bif.apply("小明", 18);
System.out.println(name);
}
}
3.6 类型[]::new
举例:数组存放
public class PullInTest05 {
//类型【】::new
public static void main(String[] args) {
// Function f1=(Integer length)->{
// return new int[length];
// };
Function f1=int[]::new;
int[] apply = f1.apply(10);
System.out.println(Arrays.toString(apply));
}
}
T表示返回结果的泛型 :无参有返回值的函数式接口
举例:随机获取0到10之间的数字
public class SupplierTest {
public static void main(String[] args) {
getNumber(()->{
return new Random().nextInt(10);
});
}
public static void getNumber(Supplier supplier){
Integer integer = supplier.get();
System.out.println("获取数字为:"+integer);
}
}
2.4 Function 函数型函数式接口
有参,有返回值
T:参数类型的泛型
R:函数返回结果的泛型
举例:将字符串转大写
public class FunctionTest {
public static void main(String[] args) {
getUpper(t->{
return t.toUpperCase(Locale.ROOT);//所传参数随便写
},"hello world");
}
public static void getUpper(Function function,String str){
String apply = function.apply(str);
System.out.println("结果为:·"+apply);
}
}
举例:计算字符串长度
public class FunctionTest02 {
public static void main(String[] args) {
getLength(t->{
return t.replace(" ","").length();
},"hello world");
}
public static void getLength(Function function,String str){
Integer apply = function.apply(str);
System.out.println("长度为:"+apply);
}
}
2.5 Predicated
boolean test(T t);确定类型为T的对象是否满足条件,并返回boolean类型
举例:判断名字是否过长
public class PredicateTest {
public static void main(String[] args) {
getNameLength(t->{
return t.length()>3?true:false;
},"迪丽热巴.迪力木拉提");
}
public static void getNameLength(Predicate predicate,String name){
boolean test = predicate.test(name);
System.out.println("名字长度是否超过3:"+test);
}
}
3.方法引用
如果我们在Lambda中所指定的功能,已经有其他方法存在相同方案,那是否还有必要再写重复逻辑?可以直接“引 用”过来就好了---方法引用
请注意其中的双冒号 :: 写法,这被称为“方法引用”,是一种新的语法
举例:计算数组和
public class PullIn {
public static void getSum(int[] arr){
int sum=0;
for (Integer i:arr) {
sum+=i;
}
System.out.println("数组和为:"+sum);
}
public static void sum(Consumer consumer){
int[] arr={1, 2, 3, 4, 5};
consumer.accept(arr);
}
public static void main(String[] args) {
//此处与上述getSum方法一模一样,造成冗余
// sum(arr->{
// int sum=0;
// for (Integer i:arr) {
// sum+=i;
// }
// System.out.println("数组和为:"+sum);
// },new int[]{1, 2, 3, 4, 5});
sum(PullIn::getSum);
}
}
3.1 什么是方法引用
方法引用是Lambda表达式的一种简写形式。如果Lambda表达式方法体只是调用一个特定的已经存在的方法,则可以使用方法引用。
常见形式:
(1)对象::方法名
(2)类名::静态方法
(3)类名::普通方法
(4)类名::new 调用的构造器
(5)String[]::new 调用数组的构造器
3.2 对象::实例方法
注意:
1.被引用的方法,参数要和接口中的抽象方法的参数一样
2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
举例:获取当前时间
public class PullInTest01 {
//对象::实例方法
public static void main(String[] args) {
Date d=new Date();
// Supplier time=()->{
// return d.getTime();
// };
//使用方法引用
Supplier time=d::getTime;
//注意:
//1.被引用的方法,参数要和接口中的抽象方法的参数一样
//2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
Long aLong = time.get();
System.out.println("aLong = "+aLong);
}
}
3.3 类名::静态方法
举例:获取当前时间
public class PullInTest02 {
//类名::静态方法
public static void main(String[] args) {
// Supplier su=()->{
// return System.currentTimeMillis();
// };
Supplier su=System::currentTimeMillis;
Long aLong = su.get();
System.out.println("aLong="+aLong);
}
}
3.4 类名::实例方法
(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
举例:字符串长度及截取字符串
public class PullInTest03 {
public static void main(String[] args) {
//类名::实例方法(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
// Function f1=(String str)->{
// return str.length();
// };
Function f1=String::length;
Integer hello = f1.apply("hello");
System.out.println("字符串长度为:"+hello);
//BiFunction f2=String::substring;
//相当于这样的Lambda
BiFunction f2=(String str,Integer index)->{
return str.substring(index);
};
String helloworld = f2.apply("helloworld", 3);
System.out.println(helloworld);
}
}
3.5 类名::new 引用类的构造器
举例:person介绍
Person类
public class Person {
private String name;
private Integer age;
public Person() {
System.out.println("调用无参构造");
}
public Person(String name, Integer age) {
System.out.println("调用有参构造"+name+"---"+age);
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + ''' +
", age=" + age +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
}
测试类
public class PullTest04 {
//类名::new 引用类的构造器
public static void main(String[] args) {
// Supplier su=()->{
// return new Person();
// };
Supplier su=Person::new;
Person person = su.get();
System.out.println(person);
// BiFunction bif=(String name,Integer age)->{
// return new Person(name,age);
// };
BiFunction bif=Person::new;
Person name = bif.apply("小明", 18);
System.out.println(name);
}
}
3.6 类型[]::new
举例:数组存放
public class PullInTest05 {
//类型【】::new
public static void main(String[] args) {
// Function f1=(Integer length)->{
// return new int[length];
// };
Function f1=int[]::new;
int[] apply = f1.apply(10);
System.out.println(Arrays.toString(apply));
}
}
有参,有返回值
T:参数类型的泛型
R:函数返回结果的泛型
举例:将字符串转大写
public class FunctionTest {
public static void main(String[] args) {
getUpper(t->{
return t.toUpperCase(Locale.ROOT);//所传参数随便写
},"hello world");
}
public static void getUpper(Function function,String str){
String apply = function.apply(str);
System.out.println("结果为:·"+apply);
}
}
举例:计算字符串长度
public class FunctionTest02 {
public static void main(String[] args) {
getLength(t->{
return t.replace(" ","").length();
},"hello world");
}
public static void getLength(Function function,String str){
Integer apply = function.apply(str);
System.out.println("长度为:"+apply);
}
}
2.5 Predicated
boolean test(T t);确定类型为T的对象是否满足条件,并返回boolean类型
举例:判断名字是否过长
public class PredicateTest {
public static void main(String[] args) {
getNameLength(t->{
return t.length()>3?true:false;
},"迪丽热巴.迪力木拉提");
}
public static void getNameLength(Predicate predicate,String name){
boolean test = predicate.test(name);
System.out.println("名字长度是否超过3:"+test);
}
}
3.方法引用
如果我们在Lambda中所指定的功能,已经有其他方法存在相同方案,那是否还有必要再写重复逻辑?可以直接“引 用”过来就好了---方法引用
请注意其中的双冒号 :: 写法,这被称为“方法引用”,是一种新的语法
举例:计算数组和
public class PullIn {
public static void getSum(int[] arr){
int sum=0;
for (Integer i:arr) {
sum+=i;
}
System.out.println("数组和为:"+sum);
}
public static void sum(Consumer consumer){
int[] arr={1, 2, 3, 4, 5};
consumer.accept(arr);
}
public static void main(String[] args) {
//此处与上述getSum方法一模一样,造成冗余
// sum(arr->{
// int sum=0;
// for (Integer i:arr) {
// sum+=i;
// }
// System.out.println("数组和为:"+sum);
// },new int[]{1, 2, 3, 4, 5});
sum(PullIn::getSum);
}
}
3.1 什么是方法引用
方法引用是Lambda表达式的一种简写形式。如果Lambda表达式方法体只是调用一个特定的已经存在的方法,则可以使用方法引用。
常见形式:
(1)对象::方法名
(2)类名::静态方法
(3)类名::普通方法
(4)类名::new 调用的构造器
(5)String[]::new 调用数组的构造器
3.2 对象::实例方法
注意:
1.被引用的方法,参数要和接口中的抽象方法的参数一样
2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
举例:获取当前时间
public class PullInTest01 {
//对象::实例方法
public static void main(String[] args) {
Date d=new Date();
// Supplier time=()->{
// return d.getTime();
// };
//使用方法引用
Supplier time=d::getTime;
//注意:
//1.被引用的方法,参数要和接口中的抽象方法的参数一样
//2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
Long aLong = time.get();
System.out.println("aLong = "+aLong);
}
}
3.3 类名::静态方法
举例:获取当前时间
public class PullInTest02 {
//类名::静态方法
public static void main(String[] args) {
// Supplier su=()->{
// return System.currentTimeMillis();
// };
Supplier su=System::currentTimeMillis;
Long aLong = su.get();
System.out.println("aLong="+aLong);
}
}
3.4 类名::实例方法
(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
举例:字符串长度及截取字符串
public class PullInTest03 {
public static void main(String[] args) {
//类名::实例方法(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
// Function f1=(String str)->{
// return str.length();
// };
Function f1=String::length;
Integer hello = f1.apply("hello");
System.out.println("字符串长度为:"+hello);
//BiFunction f2=String::substring;
//相当于这样的Lambda
BiFunction f2=(String str,Integer index)->{
return str.substring(index);
};
String helloworld = f2.apply("helloworld", 3);
System.out.println(helloworld);
}
}
3.5 类名::new 引用类的构造器
举例:person介绍
Person类
public class Person {
private String name;
private Integer age;
public Person() {
System.out.println("调用无参构造");
}
public Person(String name, Integer age) {
System.out.println("调用有参构造"+name+"---"+age);
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + ''' +
", age=" + age +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
}
测试类
public class PullTest04 {
//类名::new 引用类的构造器
public static void main(String[] args) {
// Supplier su=()->{
// return new Person();
// };
Supplier su=Person::new;
Person person = su.get();
System.out.println(person);
// BiFunction bif=(String name,Integer age)->{
// return new Person(name,age);
// };
BiFunction bif=Person::new;
Person name = bif.apply("小明", 18);
System.out.println(name);
}
}
3.6 类型[]::new
举例:数组存放
public class PullInTest05 {
//类型【】::new
public static void main(String[] args) {
// Function f1=(Integer length)->{
// return new int[length];
// };
Function f1=int[]::new;
int[] apply = f1.apply(10);
System.out.println(Arrays.toString(apply));
}
}
boolean test(T t);确定类型为T的对象是否满足条件,并返回boolean类型
举例:判断名字是否过长
public class PredicateTest {
public static void main(String[] args) {
getNameLength(t->{
return t.length()>3?true:false;
},"迪丽热巴.迪力木拉提");
}
public static void getNameLength(Predicate predicate,String name){
boolean test = predicate.test(name);
System.out.println("名字长度是否超过3:"+test);
}
}
3.方法引用
如果我们在Lambda中所指定的功能,已经有其他方法存在相同方案,那是否还有必要再写重复逻辑?可以直接“引 用”过来就好了---方法引用
请注意其中的双冒号 :: 写法,这被称为“方法引用”,是一种新的语法
举例:计算数组和
public class PullIn {
public static void getSum(int[] arr){
int sum=0;
for (Integer i:arr) {
sum+=i;
}
System.out.println("数组和为:"+sum);
}
public static void sum(Consumer consumer){
int[] arr={1, 2, 3, 4, 5};
consumer.accept(arr);
}
public static void main(String[] args) {
//此处与上述getSum方法一模一样,造成冗余
// sum(arr->{
// int sum=0;
// for (Integer i:arr) {
// sum+=i;
// }
// System.out.println("数组和为:"+sum);
// },new int[]{1, 2, 3, 4, 5});
sum(PullIn::getSum);
}
}
3.1 什么是方法引用
方法引用是Lambda表达式的一种简写形式。如果Lambda表达式方法体只是调用一个特定的已经存在的方法,则可以使用方法引用。
常见形式:
(1)对象::方法名
(2)类名::静态方法
(3)类名::普通方法
(4)类名::new 调用的构造器
(5)String[]::new 调用数组的构造器
3.2 对象::实例方法
注意:
1.被引用的方法,参数要和接口中的抽象方法的参数一样
2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
举例:获取当前时间
public class PullInTest01 {
//对象::实例方法
public static void main(String[] args) {
Date d=new Date();
// Supplier time=()->{
// return d.getTime();
// };
//使用方法引用
Supplier time=d::getTime;
//注意:
//1.被引用的方法,参数要和接口中的抽象方法的参数一样
//2.当接口抽象方法有返回值时,被引用的方法也必须有返回值
Long aLong = time.get();
System.out.println("aLong = "+aLong);
}
}
3.3 类名::静态方法
举例:获取当前时间
public class PullInTest02 {
//类名::静态方法
public static void main(String[] args) {
// Supplier su=()->{
// return System.currentTimeMillis();
// };
Supplier su=System::currentTimeMillis;
Long aLong = su.get();
System.out.println("aLong="+aLong);
}
}
3.4 类名::实例方法
(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
举例:字符串长度及截取字符串
public class PullInTest03 {
public static void main(String[] args) {
//类名::实例方法(注意:类名::实例方法实际上会将第一个参数作为方法的调用者)
// Function f1=(String str)->{
// return str.length();
// };
Function f1=String::length;
Integer hello = f1.apply("hello");
System.out.println("字符串长度为:"+hello);
//BiFunction f2=String::substring;
//相当于这样的Lambda
BiFunction f2=(String str,Integer index)->{
return str.substring(index);
};
String helloworld = f2.apply("helloworld", 3);
System.out.println(helloworld);
}
}
3.5 类名::new 引用类的构造器
举例:person介绍
Person类
public class Person {
private String name;
private Integer age;
public Person() {
System.out.println("调用无参构造");
}
public Person(String name, Integer age) {
System.out.println("调用有参构造"+name+"---"+age);
this.name = name;
this.age = age;
}
@Override
public String toString() {
return "Person{" +
"name='" + name + ''' +
", age=" + age +
'}';
}
public String getName() {
return name;
}
public void setName(String name) {
this.name = name;
}
public Integer getAge() {
return age;
}
public void setAge(Integer age) {
this.age = age;
}
}
测试类
public class PullTest04 {
//类名::new 引用类的构造器
public static void main(String[] args) {
// Supplier su=()->{
// return new Person();
// };
Supplier su=Person::new;
Person person = su.get();
System.out.println(person);
// BiFunction bif=(String name,Integer age)->{
// return new Person(name,age);
// };
BiFunction bif=Person::new;
Person name = bif.apply("小明", 18);
System.out.println(name);
}
}
3.6 类型[]::new
举例:数组存放
public class PullInTest05 {
//类型【】::new
public static void main(String[] args) {
// Function f1=(Integer length)->{
// return new int[length];
// };
Function f1=int[]::new;
int[] apply = f1.apply(10);
System.out.println(Arrays.toString(apply));
}
}



