首页 > 其他分享 >JTCR-lambda 表达式-13

JTCR-lambda 表达式-13

时间:2024-04-22 16:22:37浏览次数:14  
标签:JTCR 13 函数 接口 类型 方法 表达式 lambda

介绍

lambda 表达式本质上是一个匿名方法,用于实现函数式接口(functional interface)定义的方法。这就产生了匿名类。lambda 也称为闭包(closures)。

函数式接口是仅有一个抽象方法的接口。如 Runnable 接口仅有 run() 方法,该方法表明了接口的目的。函数式接口定义了 lambda 表达式的目标类型,lambda 表达式仅可用于特定的目标类型的上下文中。函数式接口又称 SAM 类型,SAM 指 Single Abstract Method。

Object 类中的公有方法隐式是函数式接口的成员,因为函数式接口的实例自动实现了这些方法。

-> 称为 lambda 操作符或箭头操作符,它将 lambda 表达式划分成了两个部分。左边是参数,参数可为空;右边是 lambda 体,表示 lambda 表达式的行为。lambda 体可以是单个表达式,也可以是块。

lambda 表达式出现在目标类型上下文中时,自动创建实现了函数式接口的类实例,lambda 表达式作为函数式接口中抽象方法的实现。lambda 表达式的参数类型和返回类型、参数个数必须和函数式接口中抽象方法定义的兼容、对应。

interface A {
  double get();
}

// lambda 表达式作为 get() 方法的实现
A a = () -> 1.2;

// 返回 1.2
a.get();

lambda 表达式中的参数可以指定类型,也可以不指定根据上下文自行推断。

函数式接口类型变量可以执行和它兼容的任意 lambda 表达式。

当 lambda 表达式仅有一个参数时,加不加小括号都可以。n -> n * 2 等价于 (n) -> n * 2

对于多参数 lambda 表达式,如果想为参数声明类型,则必须为所有参数声明类型。

块 lambda 表达式

-> 右边为块的 lambda 表达式称为块 lambda 表达式。使用块 lambda 表达式必须使用 return 语句。lambda 块本质上类似于方法体。

泛型函数接口

函数式接口可以是泛型接口,此时关联的 lambda 表达式的类型由泛型接口中的类型指定。

interface A<T> {}

// 类型为 Integer
A<Integer> a = (...) -> {...};

// 类型为 String
A<String> a = (...) -> {...};

lambda 表达式作参数

能接收 lambda 表达式的参数,类型必须是可以和该 lambda 表达式兼容的函数式接口。

lambda 表达式和异常

lambda 表达式中抛出异常时,函数式接口中抽象方法的 throws 子句必须有对应的异常。

lambda 表达式和变量捕获

在 lambda 表达式中,可以访问 lambda 表达式自身所在的作用域中定义的静态变量、类实例、表示该作用域的 this 等。在 lambda 表达式中访问该作用域中的局部变量的过程称为变量捕获(variable capture)。能够访问的局部变量要么是 effectively final 变量,要么是 final 修饰的变量。effectively final 变量是赋过初值之后值没有变化的变量。在 lambda 表达式中不能修改局部变量的值,在 lambda 表达式自身所在的作用域内也不能修改,因为这样做变量将不再是 effectively final。

方法引用

方法引用可以引用一个方法但不执行它。方法引用和 lambda 表达式有关,因为它也需要一个兼容函数式接口的目标类型上下文。方法引用可以创建函数式接口的实例。

静态方法的方法引用一般形式为:ClassName::methodName,可以在目标类型兼容的任何地方使用。
实例方法的方法引用一般形式为:objRef::methodName

如果想指定一个给定类的任意实例都可以使用的实例方法,而不是某个特定的类,可以这样表示方法引用:ClassName::instanceMethodName,这个方法引用对应的函数式接口中的方法需要两个参数,第一个参数匹配调用对象本身,即 ClassName 实例;第二个参数匹配 instanceMethodName 需要的参数。

interface MyFunc<T> {
    boolean func(T v1, T v2);
}

class High {
    private int h;
    public High(int h) {
        this.h = h;
    }
    boolean same(High high) {
        return h == high.h;
    }
}

public class InstanceMethod {
    static <T> int counter(T[] vals, MyFunc<T> f, T v) {
        int count = 0;
        for (int i = 0; i < vals.length; i++) {
            if (f.func(vals[i], v)) {
                count++;
            }
        }
        return count;
    }

    public static void main(String[] args) {
        int count;
        High[] week = {new High(10), new High(20), new High(31)};
        // same 与 MyFunc 接口兼容,调用 same 方法的对象作为
        // func 函数的第一个参数,传入 same 方法的对象作为 func
        // 函数的第二个参数
        count = counter(week, High::same, new High(10));
        System.out.println(count);
    }
}

泛型类、泛型方法也可以作为方法引用。泛型方法的方法引用形式为:ClassName::<Type>method,泛型类的方法引用形式为:Class<Type>::method

构造器引用

构造器引用一般形式为:Class::new,可以赋值给与构造器兼容的函数式接口类型的变量。
泛型类、泛型方法的使用与前述类似,只不过方法名是 new
数组的构造器引用形式为:type[]::new

预定义的函数接口

接口 描述
UnaryOperator<T> 对 T 类型对象使用一元操作符,返回 T 类型对象,方法为 apply()
BinaryOperator<T> 对两个 T 类型对象使用二元操作符,返回 T 类型对象,方法为 apply()
Consumer<T> 对 T 类型对象进行操作,方法为 accept()
Supplier<T> 返回 T 类型对象,方法为 get()
Function<T, R> 对 T 类型对象进行操作,返回 R 类型对象,方法为 apply()
Predicate<T> 判断 T 类型对象是否满足某个条件,据此返回 boolean 值,方法为 test()

参考

[1] Herbert Schildt, Java The Complete Reference 11th, 2019.

标签:JTCR,13,函数,接口,类型,方法,表达式,lambda
From: https://www.cnblogs.com/xdreamc/p/16403524.html

相关文章

  • JTCR-泛型-12
    什么是泛型具有参数化类型的类、接口或方法。具体的类型在运行时才确定。在泛型出现前通过使用Object引用也可以达到泛型的效果,但是缺乏类型安全检查,泛型添加了这一点。简单的泛型例子//T是类型参数,作为实际类型的占位符classGen<T>{Tv;Gen(To){v=o;......
  • JTCR-I/O,Try-with-Resources 及其他-11
    I/O基础Java的I/O操作通过流来实现。流是对输入、输出数据的抽象,每个流都和一个具体的物理实体关联,比如在输入中,流可以和键盘、磁盘文件或者网络输入等关联,虽然每个物理实体不同,但是流可以以同样的方式进行处理。Java定义了字节流和字符流。字节流处理的对象是二进制数据,以......
  • oem 135 agent升级
    [oracle@prdb1936172334]$exportORACLE_HOME=/u01/agentapp/agent_13.5.0.0.0[oracle@prdb1936172334]$unzipp33355570_135000_Generic.zip-d$ORACLE_HOME[oracle@prdb1936172334]$$ORACLE_HOME/AgentPatcher/agentpatcherapply-analyzeAgentPatcherAutomati......
  • 34天【代码随想录算法训练营34期】第八章 贪心算法 part03 (● 1005.K次取反后最大化
    1005.K次取反后最大化的数组和classSolution:deflargestSumAfterKNegations(self,nums:List[int],k:int)->int:nums.sort(key=lambdax:abs(x),reverse=True)foriinrange(len(nums)):ifnums[i]<0andk>0:......
  • Dynamics CRM 2013 批处理
    GetServiceusingSystem;usingSystem.Configuration;usingMicrosoft.Xrm.Client;usingMicrosoft.Xrm.Client.Services;usingMicrosoft.Xrm.Sdk;usingMicrosoft.Xrm.Sdk.Query;namespaceTest{classProgram{staticvoidMain(string[]args)......
  • LeetCode 1331. Rank Transform of an Array
    原题链接在这里:https://leetcode.com/problems/rank-transform-of-an-array/description/题目:Givenanarrayofintegers arr,replaceeachelementwithitsrank.Therankrepresentshowlargetheelementis.Therankhasthefollowingrules:Rankisanintegers......
  • P5897 [IOI2013] wombats
    MyBlogsP5897[IOI2013]wombats有点恐怖。首先\(R,C\)很不平衡,考虑用一棵竖着的线段树维护较大的\(R\)维,每个节点上需要存的是\(C\timesC\)的数组\(d\),\(d_{i,j}\)表示该节点的最上面一行第\(i\)个到最下面一行第\(j\)个的最短路。因为已经处理好了左右儿子内......
  • oem 135安装
      ......
  • oem 135 升级
    --安装后目录:[oracle@prdb19u01]$ls-lrttotal12drwxrwxr-x.6oracleoinstall66Sep282020appdrwxrwxr-x.3oracleoinstall30Apr2010:41agentapp--oemagent目录drwxr-x---.4oracleoinstall37Apr2012:18gc_inst--gc实例目录drwxrwxr-x......
  • CF1713F Lost Array 题解
    题目链接点击打开链接题目解法很牛的题!!!先考虑\((0,i)\)对\((j,n)\)的贡献,因为是异或,所以只要考虑奇偶性问题可以抽象成一条路径对应\(a_i\)的贡献,所以是否有\(a_i\)的贡献看\(\binom{n-i+j-1}{j-1}\)的奇偶性根据\(kummer\)定理,这个组合数是奇数当且仅当\(n-i+......