Java 8中的方法参考

sar*_*_pc 13 java lambda java-8 method-reference

public class Car {

    private int maxSpeed;

    public Car(int maxSpeed) {
        this.maxSpeed = maxSpeed;
    }

    public int getMaxSpeed() {
        return maxSpeed;
    }
}
Run Code Online (Sandbox Code Playgroud)

我们可以按以下方式对汽车列表进行排序

    Car carX = new Car(155);
    Car carY = new Car(140);

    List<Car> cars = new ArrayList<>();
    cars.add(carX);
    cars.add(carY);

    cars.sort(Comparator.comparing(Car::getMaxSpeed));
Run Code Online (Sandbox Code Playgroud)

如果我们看到方法的签名Comparator.comparing,则输入参数类型为Function<? super T, ? extends U>

在上面的例子中,是如何Car::getMaxSpeed被转换为Function<? super T, ? extends U>而以下不编译?

  Function<Void, Integer> function = Car::getMaxSpeed;
Run Code Online (Sandbox Code Playgroud)

Men*_*ena 11

那是因为getMaxSpeed方法是一个Function<Car, Integer>.

即:

<Car, Integer> Comparator<Car> java.util.Comparator.comparing(
    Function<? super Car, ? extends Integer> keyExtractor
)
Run Code Online (Sandbox Code Playgroud)

注意

为了引用getMaxSpeed来自实例Car::成语,你就必须声明Car的方法与签名:getMaxSpeed(Car car).

  • 如果`getMaxSpeed`是一个成员函数然后使用Car :: getMaxSpeed,`Car`必须声明一个成员函数`getMaxSpeed()`(无参数)或静态函数`getMaxSpeed(Car)` (4认同)
  • @saravana_pc方法引用实例方法,当这样写时,将接收器添加为第一个参数.`car :: getMaxSpeed`相当于`car - > car.getMaxSpeed()`. (2认同)

tob*_*s_k 9

如果要为不带参数的方法创建方法引用,例如已绑定到实例的方法,则应使用a Supplier,而不是Function:

Function<Car, Integer> f1 = Car::getMaxSpeed;

Car carx = new Car(42);
Supplier<Integer> f2 = carx::getMaxSpeed; 
Run Code Online (Sandbox Code Playgroud)

在方法引用中carX::getMaxSpeed,this函数的"隐式" 参数已经被绑定carx,因此你留下了一个无参数函数(顺便说一下,它不能在a中使用Comparator),在Java 8中,无参数函数只是一个Supplier.

同样,如果你有一个返回的方法void,你最终得到一个Comsumer:

Consumer<Integer> f3 = carx::setMaxSpeed;
Run Code Online (Sandbox Code Playgroud)