首页 > 代码库 > Java8闭包

Java8闭包

闭包在很多语言中都存在,例如C++,C#。闭包允许我们创建函数指针,并把它们作为参数传递,Java编程语言提供了接口的概念,接口中可以定义抽象方法,接口定义了API,并希望用户或者供应商来实现这些方法,很多时候并不是为一些接口创建独立的实现类,我们通过写一个匿名的内部类来写一个内联的接口实现,匿名内部类使用相当的广泛,匿名内部类最常见的场景就是事件处理器了,其次匿名内部类还被用于多线程中,写匿名内部类而不是创建Runable\Callable接口的实现类。

一个匿名内部类就是一个内联的给定接口的实现,这个实现类的对象作为参数传递给一个方法,然后这个方法将在内部调用传递过来的实现类的方法,这种接口叫做回调接口,这个方法叫做回调方法。

匿名内部类很多地方都在使用,在使用的同时存在一些问题

  1. 复杂

    这些类代码的层级看起来很乱很复杂,称作Vertical Problem
  2. 不能访问封装类的非final成员

    this关键字变得很迷惑,如果一个匿名类有一个与其封装类相同的成员名称,内部类会覆盖外部的成员变量,在这种情况下,外部成员在匿名类内部是不可见的,甚至不能通过this来访问。

    实例说明

        public void test() {          String variable = "Outer Method Variable";          new Thread(new Runnable() {              String variable = "Runnable Class Member";              public void run() {                  String variable = "Run Method Variable";                  System.out.println("->" + variable);                  System.out.println("->" + this.variable);             }          }).start();      } 输出
        ->Run Method Variable       ->Runnable Class Member 

    这个例子很好的说明了上面的两个问题,而Lambda表达式几乎解决上面的所有问题,我们讨论Lambda表达式之前,让我们来看看Functional Interfaces

  3. Funcational Interfaces

    一个只有单个方法的接口,这代表了这个方法的契约。
    The Single method cal exist in the form of multiple abstract methods that are inherited from superinterfaces.But in that case the inherited methods should logically represent a single method or it might redundantly declare a method that is provided by classes like Object,e.g.toString

    > interface Runnable{void run();}> interface Foo {boolean equals(Object obj);}> interface extends Foo{ int compare(String s1,String s2)}> interface Comparetor{      boolean equals(Object obj);      int compare(T t1,T t2);   }> interface Foo( int m(); Object clone();
    大多数回调接口

Java8闭包