原标题:Java 8 中的方法引用,怎么用到最好?
在Java8中,使用方法引用非常简单,如String::isEmpty,但无法使用它否定的方法引用。本文内容即如何解决此问题使得我们能够更加全面地使用方法引用。
首先看一个使用方法引用的例子:
Stream.of( "A", "", "B"). filter( String:: isEmpty).count
上面代码的输出为1,即空字符串的数目。如果我们想要获取非空字符串的数目,就不能直接使用方法引用了。
Stream.of( "A", "", "B"). filter(s -> !s. isEmpty).count
Java8中的Predicate,有predicate.negate可以转换为断言的否定形式,但String::isEmpty却无法这么做(String::isEmpty.negate或者!String::isEmpty)。
因为方法引用并不是一个 lambda或者函数接口,它能够被解析为一个或者多个函数接口。如,String::isEmpty至少可以被解析如下:
Predicate
Function
为了解决上述的问题,我们可以通过某种机制显式地将方法引用转换为一个函数接口:
publicstatic Predicate as( Predicate predicate){ returnpredicate;}
通过使用一个静态方法,接受方法引用参数,返回一个函数接口,即可实现方法引用到函数接口的转换。接着,我们就可以使用方法引用来实现上面例子中的获取非空字符串的数目。
Stream. of( "A", "", "B").filter( as( String::isEmpty).negate).count;
进一步还能使用各种组合的Predicate。
.filter( as(String::isEmpty).negate. and( "A"::equals))
由于一个方法引用可能会被解析为多种函数接口,因此如果我们实现很多参数不同的as方法,那么很容易造成混淆。 更好的方式则是在方法名中加入函数参数的类型来区分。
mport java.util.function.*;
publicclassFunctionCastUtil{
publicstatic BiConsumer asBiConsumer(BiConsumer biConsumer){
returnbiConsumer;
}
publicstatic BiFunction asBiFunction(BiFunction biFunction){
returnbiFunction;
}
publicstatic BinaryOperator asBinaryOperator(BinaryOperator binaryOperator){
returnbinaryOperator;
}
publicstatic BiPredicate asBiPredicate(BiPredicate biPredicate){
returnbiPredicate;
}
publicstaticBooleanSupplier asBooleanSupplier(BooleanSupplier booleanSupplier){
returnbooleanSupplier;
}
publicstatic Consumer asConsumer(Consumer consumer){
returnconsumer;
}
publicstaticDoubleBinaryOperator asDoubleBinaryOperator(DoubleBinaryOperator doubleBinaryOperator){
returndoubleBinaryOperator;
}
publicstaticDoubleConsumer asDoubleConsumer(DoubleConsumer doubleConsumer){
returndoubleConsumer;
}
publicstatic DoubleFunction asDoubleFunction(DoubleFunction doubleFunction){
returndoubleFunction;
}
publicstaticDoublePredicate asDoublePredicate(DoublePredicate doublePredicate){
returndoublePredicate;
}
publicstaticDoubleToIntFunction asDoubleToIntFunction(DoubleToIntFunction doubleToIntFunctiontem){
returndoubleToIntFunctiontem;
}
publicstaticDoubleToLongFunction asDoubleToLongFunction(DoubleToLongFunction doubleToLongFunction){
returndoubleToLongFunction;
}
publicstaticDoubleUnaryOperator asDoubleUnaryOperator(DoubleUnaryOperator doubleUnaryOperator){
returndoubleUnaryOperator;
}
publicstatic Function asFunction(Function function){
returnfunction;
}
publicstaticIntBinaryOperator asIntBinaryOperator(IntBinaryOperator intBinaryOperator){
returnintBinaryOperator;
}
publicstaticIntConsumer asIntConsumer(IntConsumer intConsumer){
returnintConsumer;
}
publicstatic IntFunction asIntFunction(IntFunction intFunction){
returnintFunction;
}
publicstaticIntPredicate asIntPredicate(IntPredicate intPredicate){
returnintPredicate;
}
publicstaticIntSupplier asIntSupplier(IntSupplier intSupplier){
returnintSupplier;
}
publicstaticIntToDoubleFunction asIntToDoubleFunction(IntToDoubleFunction intToDoubleFunction){
returnintToDoubleFunction;
}
publicstaticIntToLongFunction asIntToLongFunction(IntToLongFunction intToLongFunction){
returnintToLongFunction;
}
publicstaticIntUnaryOperator asIntUnaryOperator(IntUnaryOperator intUnaryOperator){
returnintUnaryOperator;
}
publicstaticLongBinaryOperator asLongBinaryOperator(LongBinaryOperator longBinaryOperator){
returnlongBinaryOperator;
}
publicstaticLongConsumer asLongConsumer(LongConsumer longConsumer){
returnlongConsumer;
}
publicstatic LongFunction asLongFunction(LongFunction longFunction){
returnlongFunction;
}
publicstaticLongPredicate asLongPredicate(LongPredicate longPredicate){
returnlongPredicate;
}
publicstatic LongSupplier asLongSupplier(LongSupplier longSupplier){
returnlongSupplier;
}
publicstaticLongToDoubleFunction asLongToDoubleFunction(LongToDoubleFunction longToDoubleFunction){
returnlongToDoubleFunction;
}
publicstaticLongToIntFunction asLongToIntFunction(LongToIntFunction longToIntFunction){
returnlongToIntFunction;
}
publicstaticLongUnaryOperator asLongUnaryOperator(LongUnaryOperator longUnaryOperator){
returnlongUnaryOperator;
}
publicstatic ObjDoubleConsumer asObjDoubleConsumer(ObjDoubleConsumer objDoubleConsumer){
returnobjDoubleConsumer;
}
publicstatic ObjIntConsumer asObjIntConsumer(ObjIntConsumer objIntConsumer){
returnobjIntConsumer;
}
publicstatic ObjLongConsumer asObjLongConsumer(ObjLongConsumer objLongConsumer){
returnobjLongConsumer;
}
publicstatic Predicate asPredicate(Predicate predicate){
returnpredicate;
}
publicstatic Supplier asSupplier(Supplier supplier){
returnsupplier;
}
publicstatic ToDoubleBiFunction asToDoubleBiFunction(ToDoubleBiFunction toDoubleBiFunction){
returntoDoubleBiFunction;
}
publicstatic ToDoubleFunction asToDoubleFunction(ToDoubleFunction toDoubleFunction){
returntoDoubleFunction;
}
publicstatic ToIntBiFunction asToIntBiFunction(ToIntBiFunction toIntBiFunction){
returntoIntBiFunction;
}
publicstatic ToIntFunction asToIntFunction(ToIntFunction ioIntFunction){
returnioIntFunction;
}
publicstatic ToLongBiFunction asToLongBiFunction(ToLongBiFunction toLongBiFunction){
returntoLongBiFunction;
}
publicstatic ToLongFunction asToLongFunction(ToLongFunction toLongFunction){
returntoLongFunction;
}
publicstatic UnaryOperator asUnaryOperator(UnaryOperator unaryOperator){
returnunaryOperator;
}
privateFunctionCastUtil{
}
}
Stream.of( "A", "", "B").filter(asPredicate(String::isEmpty).negate).count
原文:https://dzone.com/articles/put-your-java-8-method-references-to-work
译文:https://www.rowkey.me/blog/2017/09/02/java8-method-reference-work/返回搜狐,查看更多
责任编辑: