如何更好的使用Java8中方法引用详解

发布时间 - 2026-01-11 03:10:00    点击率:

前言

方法引用是用来直接访问类或者实例的已经存在的方法或者构造方法。方法引用提供了一种引用而不执行方法的方式,它需要由兼容的函数式接口构成的目标类型上下文。计算时,方法引用会创建函数式接口的一个实例。

当Lambda表达式中只是执行一个方法调用时,不用Lambda表达式,直接通过方法引用的形式可读性更高一些。方法引用是一种更简洁易懂的Lambda表达式。

注意:方法引用是一个Lambda表达式,其中方法引用的操作符是双冒号"::"。

在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<String>
Function<String, Boolean>

为了解决上述的问题,我们可以通过某种机制显式地将方法引用转换为一个函数接口:

public static <T> Predicate<T> as(Predicate<T> predicate) {
 return predicate;
}

通过使用一个静态方法,接受方法引用参数,返回一个函数接口,即可实现方法引用到函数接口的转换。接着,我们就可以使用方法引用来实现上面例子中的获取非空字符串的数目。

Stream.of("A", "", "B").filter(as(String::isEmpty).negate()).count();

进一步还能使用各种组合的Predicate。

.filter(as(String::isEmpty).negate().and("A"::equals))

由于一个方法引用可能会被解析为多种函数接口,因此如果我们实现很多参数不同的as方法,那么很容易造成混淆。更好的方式则是在方法名中加入函数参数的类型来区分。

import java.util.function.*;

public class FunctionCastUtil {
 public static <T, U> BiConsumer<T, U> asBiConsumer(BiConsumer<T, U> biConsumer) {
 return biConsumer;
 }
 public static <T, U, R> BiFunction<T, U, R> asBiFunction(BiFunction<T, U, R> biFunction) {
 return biFunction;
 }
 public static <T> BinaryOperator<T> asBinaryOperator(BinaryOperator<T> binaryOperator) {
 return binaryOperator;
 }
 public static <T, U> BiPredicate<T, U> asBiPredicate(BiPredicate<T, U> biPredicate) {
 return biPredicate;
 }
 public static BooleanSupplier asBooleanSupplier(BooleanSupplier booleanSupplier) {
 return booleanSupplier;
 }
 public static <T> Consumer<T> asConsumer(Consumer<T> consumer) {
 return consumer;
 }
 public static DoubleBinaryOperator asDoubleBinaryOperator(DoubleBinaryOperator doubleBinaryOperator) {
 return doubleBinaryOperator;
 }
 public static DoubleConsumer asDoubleConsumer(DoubleConsumer doubleConsumer) {
 return doubleConsumer;
 }
 public static <R> DoubleFunction<R> asDoubleFunction(DoubleFunction<R> doubleFunction) {
 return doubleFunction;
 }
 public static DoublePredicate asDoublePredicate(DoublePredicate doublePredicate) {
 return doublePredicate;
 }
 public static DoubleToIntFunction asDoubleToIntFunction(DoubleToIntFunction doubleToIntFunctiontem) {
 return doubleToIntFunctiontem;
 }
 public static DoubleToLongFunction asDoubleToLongFunction(DoubleToLongFunction doubleToLongFunction) {
 return doubleToLongFunction;
 }
 public static DoubleUnaryOperator asDoubleUnaryOperator(DoubleUnaryOperator doubleUnaryOperator) {
 return doubleUnaryOperator;
 }
 public static <T, R> Function<T, R> asFunction(Function<T, R> function) {
 return function;
 }
 public static IntBinaryOperator asIntBinaryOperator(IntBinaryOperator intBinaryOperator) {
 return intBinaryOperator;
 }
 public static IntConsumer asIntConsumer(IntConsumer intConsumer) {
 return intConsumer;
 }
 public static <R> IntFunction<R> asIntFunction(IntFunction<R> intFunction) {
 return intFunction;
 }
 public static IntPredicate asIntPredicate(IntPredicate intPredicate) {
 return intPredicate;
 }
 public static IntSupplier asIntSupplier(IntSupplier intSupplier) {
 return intSupplier;
 }
 public static IntToDoubleFunction asIntToDoubleFunction(IntToDoubleFunction intToDoubleFunction) {
 return intToDoubleFunction;
 }
 public static IntToLongFunction asIntToLongFunction(IntToLongFunction intToLongFunction) {
 return intToLongFunction;
 }
 public static IntUnaryOperator asIntUnaryOperator(IntUnaryOperator intUnaryOperator) {
 return intUnaryOperator;
 }
 public static LongBinaryOperator asLongBinaryOperator(LongBinaryOperator longBinaryOperator) {
 return longBinaryOperator;
 }
 public static LongConsumer asLongConsumer(LongConsumer longConsumer) {
 return longConsumer;
 }
 public static <R> LongFunction<R> asLongFunction(LongFunction<R> longFunction) {
 return longFunction;
 }
 public static LongPredicate asLongPredicate(LongPredicate longPredicate) {
 return longPredicate;
 }
 public static <T> LongSupplier asLongSupplier(LongSupplier longSupplier) {
 return longSupplier;
 }
 public static LongToDoubleFunction asLongToDoubleFunction(LongToDoubleFunction longToDoubleFunction) {
 return longToDoubleFunction;
 }
 public static LongToIntFunction asLongToIntFunction(LongToIntFunction longToIntFunction) {
 return longToIntFunction;
 }
 public static LongUnaryOperator asLongUnaryOperator(LongUnaryOperator longUnaryOperator) {
 return longUnaryOperator;
 }
 public static <T> ObjDoubleConsumer<T> asObjDoubleConsumer(ObjDoubleConsumer<T> objDoubleConsumer) {
 return objDoubleConsumer;
 }
 public static <T> ObjIntConsumer<T> asObjIntConsumer(ObjIntConsumer<T> objIntConsumer) {
 return objIntConsumer;
 }
 public static <T> ObjLongConsumer<T> asObjLongConsumer(ObjLongConsumer<T> objLongConsumer) {
 return objLongConsumer;
 }
 public static <T> Predicate<T> asPredicate(Predicate<T> predicate) {
 return predicate;
 }
 public static <T> Supplier<T> asSupplier(Supplier<T> supplier) {
 return supplier;
 }
 public static <T, U> ToDoubleBiFunction<T, U> asToDoubleBiFunction(ToDoubleBiFunction<T, U> toDoubleBiFunction) {
 return toDoubleBiFunction;
 }
 public static <T> ToDoubleFunction<T> asToDoubleFunction(ToDoubleFunction<T> toDoubleFunction) {
 return toDoubleFunction;
 }
 public static <T, U> ToIntBiFunction<T, U> asToIntBiFunction(ToIntBiFunction<T, U> toIntBiFunction) {
 return toIntBiFunction;
 }
 public static <T> ToIntFunction<T> asToIntFunction(ToIntFunction<T> ioIntFunction) {
 return ioIntFunction;
 }
 public static <T, U> ToLongBiFunction<T, U> asToLongBiFunction(ToLongBiFunction<T, U> toLongBiFunction) {
 return toLongBiFunction;
 }
 public static <T> ToLongFunction<T> asToLongFunction(ToLongFunction<T> toLongFunction) {
 return toLongFunction;
 }
 public static <T> UnaryOperator<T> asUnaryOperator(UnaryOperator<T> unaryOperator) {
 return unaryOperator;
 }
 private FunctionCastUtil() {
 }
}

Stream.of("A", "", "B").filter(asPredicate(String::isEmpty).negate()).count();

英文原文:https://dzone.com/articles/put-your-java-8-method-references-to-work

总结

以上就是这篇文章的全部内容了,希望本文的内容对大家的学习或者工作能带来一定的帮助,如果有疑问大家可以留言交流,谢谢大家对的支持。


# java8  # 方法引用  # 参数  # java  # Java8中如何通过方法引用获取属性名详解  # Java8新特性:Lambda表达式之方法引用详解  # Java8 Lamda方法引用和构造引用原理  # 30分钟入门Java8之方法引用学习  # Java8中方法引用的使用详解  # 使用java8的方法引用替换硬编码的示例代码  # Java8方法引用及构造方法引用原理实例解析  # Java8方法引用和构造引用代码实例  # java8新特性之方法引用示例代码  # 你真的会使用Java的方法引用吗  # 是一个  # 转换为  # 空字符串  # 一个函数  # 是一种  # 多个  # 还能  # 则是  # 很容易  # 我们可以  # 而不  # 英文  # 更高  # 就不能  # 这么做  # 这篇文章  # 谢谢大家  # 来实现  # 如何解决  # 就可以 


相关栏目: 【 网站优化151355 】 【 网络推广146373 】 【 网络技术251813 】 【 AI营销90571


相关推荐: JS中使用new Date(str)创建时间对象不兼容firefox和ie的解决方法(两种)  Laravel如何与Docker(Sail)协同开发?(环境搭建教程)  香港服务器网站推广:SEO优化与外贸独立站搭建策略  Laravel Debugbar怎么安装_Laravel调试工具栏配置指南  Laravel怎么实现API接口鉴权_Laravel Sanctum令牌生成与请求验证【教程】  Laravel模型关联查询教程_Laravel Eloquent一对多关联写法  使用Dockerfile构建java web环境  什么是JavaScript解构赋值_解构赋值有哪些实用技巧  实例解析Array和String方法  悟空浏览器如何设置小说背景色_悟空浏览器背景色设置【方法】  济南网站建设制作公司,室内设计网站一般都有哪些功能?  活动邀请函制作网站有哪些,活动邀请函文案?  HTML5空格和margin有啥区别_空格与外边距的使用场景【说明】  如何在阿里云域名上完成建站全流程?  Laravel怎么为数据库表字段添加索引以优化查询  详解免费开源的DotNet二维码操作组件ThoughtWorks.QRCode(.NET组件介绍之四)  Laravel安装步骤详细教程_Laravel环境搭建指南  标题:Vue + Vuex + JWT 身份认证的正确实践与常见误区解析  小米17系列还有一款新机?主打6.9英寸大直屏和旗舰级影像  安克发布新款氮化镓充电宝:体积缩小 30%,支持 200W 输出  Laravel中的Facade(门面)到底是什么原理  如何续费美橙建站之星域名及服务?  如何打造高效商业网站?建站目的决定转化率  香港服务器租用费用高吗?如何避免常见误区?  JavaScript如何实现音频处理_Web Audio API如何工作?  焦点电影公司作品,电影焦点结局是什么?  Laravel distinct去重查询_Laravel Eloquent去重方法  Laravel如何使用withoutEvents方法临时禁用模型事件  网站广告牌制作方法,街上的广告牌,横幅,用PS还是其他软件做的?  如何在Windows 2008云服务器安全搭建网站?  Laravel Seeder怎么填充数据_Laravel数据库填充器的使用方法与技巧  微信小程序 wx.uploadFile无法上传解决办法  Android GridView 滑动条设置一直显示状态(推荐)  Laravel如何升级到最新的版本_Laravel版本升级流程与兼容性处理  Laravel用户认证怎么做_Laravel Breeze脚手架快速实现登录注册功能  php静态变量怎么调试_php静态变量作用域调试技巧【解答】  Laravel如何记录自定义日志?(Log频道配置)  Laravel如何使用查询构建器?(Query Builder高级用法)  Laravel Blade组件怎么用_Laravel可复用视图组件的创建与使用  如何用AWS免费套餐快速搭建高效网站?  深圳网站制作的公司有哪些,dido官方网站?  Windows Hello人脸识别突然无法使用  Laravel怎么创建自己的包(Package)_Laravel扩展包开发入门到发布  如何快速查询域名建站关键信息?  北京网页设计制作网站有哪些,继续教育自动播放怎么设置?  Python文本处理实践_日志清洗解析【指导】  Laravel如何实现数据导出到CSV文件_Laravel原生流式输出大数据量CSV【方案】  微信公众帐号开发教程之图文消息全攻略  如何挑选高效建站主机与优质域名?  微信小程序 配置文件详细介绍