JDK提供了大量的函数式接口,方便咱们开发的时候无需本身编写接口,这些接口都比较通用,学会他们而且在工做中使用,不只方便的解决问题,并且十分优雅。
Supplier接口的源码比较简单,只有一个方法。函数
@FunctionalInterface public interface Supplier<T> { /** * Gets a result. * * @return a result */ T get(); }
get方法没有参数,可是有一个返回值,该返回值是泛型参数指定的类型。该方法用于建立指定类型的对象。测试
在尝试使用Supplier接口以前,咱们先看这样的一个场景:尝试从某个地方获取一个对象,若是没有获取到,那么咱们就本身造一个默认的对象。this
咱们先定义一个对象Person.code
public class Person { private final String name; private final Integer age; public Person(String name, Integer age){ this.name = name; this.age = age; } }
如今来测试:getPerson 方法经过 name 来从列表中查找Person对象,若是查到就返回,没有查到返回 null. 在main方法中咱们调用该方法,而且判断返回结果为空的时候就建立一个默认的Person 对象,而后继续后面的逻辑。对象
public class SupplierTest { private static List<Person> personList = new ArrayList<Person>() { { add(new Person("lisi", 20)); add(new Person("zhangsan", 23)); } }; public static void main(String[] args) { String name = "wangwu"; Person person = getPerson(name); if (person == null) { person = new Person(name, 10); } //后续处理 System.out.println(person); } public static Person getPerson(String name) { for (Person person : personList) { if (person.getName().equals(name)) { return person; } } return null; } }
上面的这种写法虽然能解决问题,但如今可使用Supplier简化代码。接口
public class SupplierTest { private static List<Person> personList = new ArrayList<Person>() { { add(new Person("lisi", 20)); add(new Person("zhangsan", 23)); } }; public static void main(String[] args) { String name = "wangwu"; Person person = getPerson(name, () -> new Person(name, 10)); //后续处理 System.out.println(person); } public static Person getPerson(String name, Supplier<Person> supplier) { return personList.stream() .filter(e -> e.getName().equals(name)) .findAny() .orElse(supplier.get()); } }
这里咱们在 getPerson
方法中添加了一个参数 Supplier<Person> supplier
,在没有获取到须要寻找的对象的时候,由调用方提供的Supplier来生成一个默认的对象。那么咱们在main方法中调用 getPerson
的时候就无需进行空判断,代码也就比较清楚简单。开发
Person person = getPerson(name, () -> new Person(name, 10));
这种模式看起来很是直观,对于这种场景应该鼓励使用。getPerson的第一个参数是name,若是使用该name值查找到Person对象,那么就使用它,若是查找为空,那么咱们本身建立一个默认的Person实例,也就是上面的Lambda表达式的内容。get