实例方法引用是Lambda表达式的替代写法,格式为对象名::实例方法,需同时满足:调用已有对象的实例方法且参数列表完全匹配。

Java 中实例方法引用不是直接“在 Lambda 里写”,而是作为 Lambda 表达式的替代写法——当 Lambda 体只做一件事:调用某个对象的实例方法,且参数匹配时,就可以用 对象名::实例方法 替代整个 Lambda。
什么时候能用实例方法引用
必须同时满足两个条件:
- Lambda 表达式只调用一个已有对象的实例方法(不是静态方法,也不是 new 出来的临时对象)
- Lambda 参数列表和该实例方法的参数列表顺序、类型、数量完全一致(第一个参数就是被调用方法的主调对象,但这里不适用——那是“特定类的方法引用”;实例方法引用要求主调对象已存在)
基本写法:对象名::方法名
假设你有一个字符串对象 str = "hello",想把它传给 Consumer<string></string> 做打印:
普通 Lambda 写法:
立即学习“Java免费学习笔记(深入)”;
更现实的例子:用 System.out 的 println 方法:
等价的实例方法引用写法:
Consumer<String> c3 = System.out::println;因为 System.out 是一个 PrintStream 实例,println(String) 是它的实例方法,且 Lambda 参数 s 正好作为该方法的唯一入参。
常见错误点
- 不能写成
"abc"::toUpperCase—— 字符串字面量是常量,虽是对象,但编译器通常不鼓励对字面量做方法引用(部分版本支持,但语义不清,易出错) - 不能写成
new ArrayList<>()::add—— 每次都 new 新对象,引用的是临时实例,可能引发意料外的行为或内存问题 - 如果要引用“某个具体对象”的方法,这个对象必须是已声明、可访问的变量,比如
list::add(list是提前定义好的ArrayList变量)
对比:实例方法引用 vs 特定类的方法引用
别混淆这两个:
-
实例方法引用:
obj::method→obj是确定的对象,方法调用目标固定 -
特定类的方法引用:
String::compareToIgnoreCase→ 不指定具体对象,第一个参数自动作为主调对象(类似(s1, s2) -> s1.compareToIgnoreCase(s2))


















