Posted on 2020-07-24 15:46
為自己代言 閱讀(1330)
評論(0) 編輯 收藏 所屬分類:
java/J2EE
函數式接口的特征
1、三種方法
- 唯一的抽象方法
- 使用default定義普通方法(默認方法),通過對象調用。
- 使用static定義靜態方法,通過接口名調用。
2、一個新注解@FunctionInterface
- 注解@FunctionalInterface告訴編譯器這是一個函數式接口,明確這個函數中只有一個抽象方法,當你嘗試在接口中編寫多個抽象方法的時候編譯器將不允許,但是可以有多個非抽象方法。
- 不過Object類的方法可以定義為抽象方法,因為接口的實現類一定是Object的子類
- 如果接口被標注了@FunctionalInterface,這個類就必須符合函數式接口的規范
- 即使一個接口沒有標注@FunctionalInterface,如果這個接口滿足函數式接口規則,依舊被當作函數式接口。
3、JDK 1.8 新增加的函數接口包:
java.util.function.*
java.util.function 它包含了很多接口,用來支持 Java的 函數式編程,它們大致分為五類:

4、代碼樣例
/**
*JDK 8 函數式接口 Supplier、Function、Consumer、Predicate
*
* @param args
* @throws Exception
*/ public static void main(String[] args) throws Exception { ThreadPoolExecutor executor = (ThreadPoolExecutor)newFixedThreadPool(10); //1:JDK8以前,通過匿名內部類實現函數式接口
executor.submit(new Runnable() { @Override public void run() { System.out.println("JDK8以前,通過匿名內部類實現函數式接口"); } }); //2:JDK8以后可以使用lambda 表達式來實現,lambda表達式就是為了優化匿名內部類而生(分開寫效果)
Thread thread = new Thread(() -> System.out.println("task running !")); Runnable r = () -> System.out.println("JDK8以后可以使用lambda 表達式來實現,lambda表達式就是為了優化匿名內部類而生(分開寫效果)!"); executor.submit(r); //3:合并起來效果
executor.submit(() -> { System.out.println("JDK8以后可以使用lambda 表達式來實現,lambda表達式就是為了優化匿名內部類而生!"); }); //4:其它 Supplier、Function、Consumer、Predicate 都可以用lambda 表達式來實現
Supplier<String> supplier = () -> "我是SuSupplier"; Supplier<Integer> supplier2 = () -> new Integer(1); System.out.println("supplier=" + supplier.get() + ";supplier2=" + supplier2.get()); //5: Function功能型函數式接口 Function<T, R> 接受一個輸入參數T,返回一個結果R
Function<String,Integer> function=str -> Integer.parseInt(str); Function<Integer,String> fun2 = item -> item+""; System.out.println("輸入字符型 1 返回int型結果:"+function.apply("1")); System.out.println("輸入整型 1 返回字符型結果:"+fun2.apply(2)); //6: Consumer 一個接受單個輸入參數并且不返回結果的操作。 與大多數其他函數接口不同, Consumer接口期望通過接受參數,改普通對象引用值(說明白點就是對原來的值進行加工,注意返回值 void)
Consumer<StringBuffer> consumer= sb->sb.append("-yyy"); StringBuffer sb1=new StringBuffer().append("111"); consumer.accept(sb1); //改變sb的內部引用值
System.out.println("=========s="+sb1.toString()); //7: Predicate<T> 斷言型接口常用于集合的過濾,得到一個新的集合 Stream filter(Predicate<? super T> predicate);
Predicate<Integer> predicate = age -> age > 18; Predicate<String> predicate2 = str -> str != null; System.out.println(predicate.test(19)); System.out.println(predicate2.test(null)); //我們常用集合過濾類就是對這個接口實現類 其中 filter(Predicate<? super T> predicate) 用的就是這個接口
List<String> list= Lists.newArrayList("1","2","2","3","4","4","8"); list.stream().map(s -> Long.parseLong(s)).distinct().filter(s -> s < 10).collect(Collectors.toList()).forEach(u -> System.out.println(u)); //總結,以上的例子其實都是JDK8 lambda 表達式簡潔的寫法,而且全是合并寫的,并沒有分開步驟寫(所有函數性接口,都可以用lambda 表達式簡潔寫法)
//關閉線程池
executor.shutdownNow(); }