本文将详细解释消费者接口和谓词接口的最初使用。文章内容质量较高,边肖将分享给大家参考。希望你看完这篇文章后有所了解。
Consumer 接口
源码
package Java . util . function;
import Java . util . objects;
@ FunctionalInterface
publicinterfaceConsumerT {
无效接受(TT);
默认消费者然后(消费者?superTafter){ 0
Objects.requireNonNull(在之后);
返回(TT)-{接受(t);after.accept};
}
}从源代码可以看出,Consumer接口是一个函数接口,这个函数接口唯一的抽象方法没有返回值。也许每个人都会有疑惑,都没有返回值,那么这个接口有什么用呢?当然,这个接口不会向我们返回任何值,但是我们可以使用它来修改传递的参数。这比直接修改有什么优势?呃,自己挖坑?我说不出我有什么优点。我还是比较弱,但是我喜欢这种编程方法。
00-1010,例如,如果用户名为空,则可以为他设置默认名称。我想不出一个好的例子,但我觉得这个例子不太合理,但它有类似的意思。
User.java:
packageentity
publicclassUser{
//用户的默认名称
publicationstatifinderingdefault _ NAME='彭明伟';
//用户年龄
私人占有;
//用户名
privateStringname
publiintgetage(){ 0
返回;
}
public void setage(intage){ 0
this.age=年龄;
}
public stringgetname(){ 0
returnname
}
public void setname(Stringname){ 0
this.name=name
}
}testConsumer.java:
packagetest
重要。用户;
import Java . util . function . consumer;
publicclasstestConsumer{
public static void main(String[] args){
Consumer<User> consumer = user -> user.setName(User.DEFAULT_NAME);
User user = new User();
if(user.getName() == null) consumer.accept(user);
System.out.println(user.getName());
}
}
输出:Kaven
使用 andThen()
从源码可以得到,this 进行 accept() 后,after 再进行 accept(),相当于进行了两次 accept() 。
default Consumer<T> andThen(Consumer<? super T> after) { Objects.requireNonNull(after); return (T t) -> { accept(t); after.accept(t); }; }
下面以小学成绩单为例,假设小学成绩单是由两门单科成绩(语文、数学)和总分组成,当我们需要修改其中一门成绩的时候,我们是不是也需要修改总分呢?这是肯定的啊。当然,这个例子也不是很合理。
Grade.java:
package entity; public class Grade { // 语文成绩 private int chinese_language; // 英语成绩 private int english; // 总分 private int total_score; public Grade(int chinese_language, int english){ this.chinese_language = chinese_language; this.english = english; this.total_score = chinese_language + english; } public int getChinese_language() { return chinese_language; } public void setChinese_language(int chinese_language) { this.chinese_language = chinese_language; } public int getEnglish() { return english; } public void setEnglish(int english) { this.english = english; } public int getTotal_score() { return this.total_score; } public void setTotal_score() { this.total_score = this.chinese_language + this.english; } }
testConsumerAndThen.java:
package test; import entity.Grade; import java.util.function.Consumer; public class testConsumerAndThen { public static void main(String[] args){ Consumer<Grade> total_score = grade -> { grade.setTotal_score(); }; Consumer<Grade> english = grade -> { grade.setEnglish(80); }; Grade grade = new Grade(80,70); System.out.printf("英语成绩为:%d\n",grade.getEnglish()); System.out.printf("总分为:%d\n",grade.getTotal_score()); english.andThen(total_score).accept(grade); System.out.println("修改英语成绩后---------------"); System.out.printf("英语成绩为:%d\n",grade.getEnglish()); System.out.printf("总分为:%d\n",grade.getTotal_score()); } }
输出:
英语成绩为:70
总分为:150
修改英语成绩后---------------
英语成绩为:80
总分为:160
Predicate 接口
源码
package java.util.function; import java.util.Objects; @FunctionalInterface public interface Predicate<T> { boolean test(T t); default Predicate<T> and(Predicate<? super T> other) { Objects.requireNonNull(other); return (t) -> test(t) && other.test(t); } default Predicate<T> negate() { return (t) -> !test(t); } default Predicate<T> or(Predicate<? super T> other) { Objects.requireNonNull(other); return (t) -> test(t) || other.test(t); } static <T> Predicate<T> isEqual(Object targetRef) { return (null == targetRef) ? Objects::isNull : object -> targetRef.equals(object); } }
Predicate 接口也是函数式接口,调用接口的 test 方法会返回一个布尔类型的值,其实从 Predicate 接口的源码中也可以看出来,这个接口的用处是什么。
以我的理解,是可以用来判断传递过来的参数是否匹配一些条件。
使用 test()
我们还是使用 Consumer 接口的例子,当用户的 name 为 null 时,给用户设置默认的 name。
我们可以用 Predicate 接口来判断用户的 name 是否为空,可能看起来比直接比较麻烦一点。
testPredicate.java:
package test; import entity.User; import java.util.function.Consumer; import java.util.function.Predicate; public class testPredicate { public static void main(String[] args){ Consumer<User> consumer = user -> user.setName(User.DEFAULT_NAME); Predicate<User> predicate = user -> { return user.getName() == null ; }; User user = new User(); if(predicate.test(user)) consumer.accept(user); System.out.println(user.getName()); } }
输出:Kaven
一样的效果。
使用 negate()
从源码中可以得到,negate() 是返回一个对 test() 的结果取一次反的 Predicate 实例。
default Predicate<T> negate() { return (t) -> !test(t); }
也可以这样用,负负得正不是吗。
if(!predicate.negate().test(user)) consumer.accept(user);
使用 and()
and() 返回一个对两个 test() 以 && 的方式的 Predicate 实例。
default Predicate<T> and(Predicate<? super T> other) { Objects.requireNonNull(other); return (t) -> test(t) && other.test(t); }
在 User.java 里面加一个用户默认年龄属性。
// 用户默认年龄 public static final int DEFAULT_AGE = 20;
当用户年龄不符合情况并且名字为空时,就重新设置用户的年龄和名字。
testPredicate.java:
package test; import entity.User; import java.util.function.Consumer; import java.util.function.Predicate; public class testPredicate { public static void main(String[] args){ Consumer<User> consumer = user -> user.setName(User.DEFAULT_NAME); Consumer<User> consumer_age = user -> user.setAge(User.DEFAULT_AGE); Predicate<User> predicate = user -> { return user.getName() == null ; }; Predicate<User> predicate_age = user -> { int age = user.getAge(); return (age <= 0 || age >=150); }; User user = new User(); if(predicate.and(predicate_age).test(user)) consumer.andThen(consumer_age).accept(user); System.out.println(user.getName()); System.out.println(user.getAge()); } }
输出:
Kaven
20
Predicate接口还有两个方法:
-
or()
or() 方法应该很容易理解,or() 返回一个对两个 test() 以 || 的方式的 Predicate 实例。
default Predicate<T> or(Predicate<? super T> other) { Objects.requireNonNull(other); return (t) -> test(t) || other.test(t); }
-
isEqual()
接口的静态方法,看源码也很容易理解,生成一个判断是否与 targetRef equal的 Predicate 实例。targetRef 不为 null 时,如果 targetRef 这个实例的类中没有重载 Object 类的 equals() 方法或者 targetRef 这个实例本身就是 Object 类的实例,就会使用 Object 类的 equals() 进行判断,就只会判断传递过来的参数的引用是否与 targetRef 一样,和 == 相同。
static <T> Predicate<T> isEqual(Object targetRef) { return (null == targetRef) ? Objects::isNull : object -> targetRef.equals(object); }
从 Object 类的源码也很容易看出来,equals() 就是直接使用的 == 进行判断的。
public boolean equals(Object obj) { return (this == obj); }
要想使用自己的 equals() 进行判断,就在 targetRef 实例的类中重写 equals() 方法。
比如在 User.java 中重写 equals():
@Override public boolean equals(Object obj) { if(obj == null) return false; else{ if(obj instanceof User){ User user = (User) obj; // String 类已经重载了 equals() if(this.name.equals((user).name) && this.age == user.age) return true; else return false; } else return false; } }
使用 or()、isEqual()
package test; import entity.User; import java.util.function.Consumer; import java.util.function.Predicate; public class testPredicate { public static void main(String[] args){ Consumer<User> consumer = user -> user.setName(User.DEFAULT_NAME); Consumer<User> consumer_age = user -> user.setAge(User.DEFAULT_AGE); Predicate<User> predicate = user -> { return user.getName() == null ; }; Predicate<User> predicate_age = user -> { int age = user.getAge(); return (age <= 0 || age >=150); }; User user = new User(); user.setAge(21); if(predicate.or(predicate_age).test(user)) consumer.andThen(consumer_age).accept(user); // if(predicate.and(predicate_age).test(user)) consumer.andThen(consumer_age).accept(user); // if(!predicate.negate().test(user)) consumer.accept(user); // if(predicate.test(user)) consumer.accept(user); User user_equal = new User(User.DEFAULT_AGE , User.DEFAULT_NAME); System.out.println(Predicate.isEqual(user).test(user_equal)); System.out.println(user.equals(user_equal)); System.out.println(user.getName()); System.out.println(user.getAge()); } }
输出:
true
true
Kaven
20
关于基于Consumer接口、Predicate接口初使用是怎样的就分享到这里了,希望
内容来源网络,如有侵权,联系删除,本文地址:https://www.230890.com/zhan/153810.html