函数式接口:只有一个方法的接口
比如:Runnable接口,forEach接口…….
@FunctionalInterface
public interface Runnable {
/**
* When an object implementing interface <code>Runnable</code> is used
* to create a thread, starting the thread causes the object's
* <code>run</code> method to be called in that separately executing
* thread.
* <p>
* The general contract of the method <code>run</code> is that it may
* take any action whatsoever.
*
* @see java.lang.Thread#run()
*/
public abstract void run();
}
四大原生函数式接口
Function:范型<T,R> T会作为参数,R则是返回值
@FunctionalInterface
public interface Function<T, R> {
/**
* Applies this function to the given argument.
*
* @param t the function argument
* @return the function result
*/
R apply(T t);
举个例子
public static void main(String[] args)
{
//函数式接口
Function function = new Function<String,Integer>()
{
@Override
public Integer apply(String o)
{
return 1;
}
};
System.out.println(function.apply("Y1"));
}
运行结果:
1
还可以用 Lambda 这么写
Function functionLambda = (Y1)->{return 1;};
System.out.println(functionLambda.apply("Y1"));
Function functionLambda = Y1->{return 1;};
System.out.println(functionLambda.apply("Y1"));
Predicate(断定型接口):范型<T> T会作为参数,根据逻辑返回布尔值
@FunctionalInterface
public interface Predicate<T> {
/**
* Evaluates this predicate on the given argument.
*
* @param t the input argument
* @return {@code true} if the input argument matches the predicate,
* otherwise {@code false}
*/
boolean test(T t);
举个例子
public static void main(String[] args)
{
Predicate predicate = new Predicate<String>()
{
//判断字符串长度是否大于3
@Override
public boolean test(String o)
{
return o.length()>3;
}
};
System.out.println(predicate.test("Y1"));
}
运行结果:
false
当然也可以用Lambda
Predicate predicate = Y1->{
if (Y1 instanceof String){
String o = (String) Y1;
return o.length()>3;
}else {
return false;
}
};
System.out.println(predicate.test("Y111"));
运行结果:
true
或者更加简化
Predicate<String> predicate = Y1->{return Y1.length()>3;};
System.out.println(predicate.test("Y111"));
Consumer(消费型接口) 范型<T> T会作为参数,没有返回值
@FunctionalInterface
public interface Consumer<T> {
/**
* Performs this operation on the given argument.
*
* @param t the input argument
*/
void accept(T t);
举个例子
public static void main(String[] args)
{
Consumer<String> consumer = new Consumer<String>()
{
@Override
public void accept(String o)
{
System.out.println(o);
}
};
consumer.accept("Y1");
}
运行结果:
Y1
Lambda
Consumer<String> consumer = Y1->{ System.out.println(Y1); };
consumer.accept("Y1”);
运行结果:
Y1
Supplier(供给型接口) 没有参数只有返回值
@FunctionalInterface
public interface Supplier<T> {
/**
* Gets a result.
*
* @return a result
*/
T get();
}
举个例子
public static void main(String[] args)
{
Supplier<String> supplier = new Supplier<String>()
{
@Override
public String get()
{
return "Y1";
}
};
System.out.println(supplier.get());
}
运行结果:
Y1
Lambda
Supplier<String> supplier = ()->{return "Y1";};
System.out.println(supplier.get());
运行结果:
Y1
函数式接口简化类编程模型,框架底层应用比较多,下面的流式计算会用到很多函数式接口
Stream流式计算
看一个例子:
public class StreamDemo
{
public static void main(String[] args)
{
/*
要求用一行代码实现
现在有6个用户
筛选:
ID 必须是偶数
年龄必须大于3岁
用户名转为大写字母
用户名字母倒着排序
只输出一个用户的名字
*/
User user1 = new User(1,"a",1);
User user2 = new User(2,"b",2);
User user3 = new User(3,"c",3);
User user4 = new User(4,"d",4);
User user5 = new User(5,"e",5);
User user6 = new User(6,"f",6);
}
}
这时候就要用到链式编程,lambda表达式,函数式接口,还有Stream流式计算
//集合负责存储
List<User> users = Arrays.asList(user1, user2, user3, user4, user5,user6);
//计算交给stream流
users.stream()
.filter(user -> {return user.getId()%2==0;}) // id偶数
.filter(user -> {return user.getAge()>3;}) //年龄大于三
.map(user -> {return user.getName().toUpperCase();}) //名字变成大大写
.sorted((u1,u2) -> {return u2.compareTo(u1);}) //倒排序
.limit(1) //输出一个用户
.forEach(System.out::print);
运行结果
F