语法糖:lambda表达式

语法糖:lambda表达式

用法:

一.用来当做集合类的遍历

  注意点:

1.无法使用continue,break等 用于一般foreach循环的;可用return 此处用法与continue等同;

2.无法在编译期,去改变循环外的对象的引用,或者是基本类型的值;

	        Integer[] a = new Integer[]{1,2,3,4,5};
	        List b = Arrays.asList(a);
	        b.forEach(c->{
	            if (2==c){
	                return;
	            }
	            System.out.println("c = " + c);
	        });

Lambda与匿名内部类在访问外部变量时,都不允许有修改变量的倾向,即若:

1

2

3

4

5

6

7

8

final double a  = 3.141592;

double b = 3.141592;

 

DoubleUnaryOperator anotherDoubleUnaryOperator = x -> {

    a = 2// ERROR

    b = 3// ERROR

    return 0.0;

    };

  

则:

  • 无法改变final量的值
  • 不允许在Lambda表达式中修改使用的(外部)变量

相应的报错信息:

  • Cannot assign a value to final variable
  • Variable used in lambda expression should be final or effectively final

由是观之,我们将Lambda的这种变量捕获行为称之为值捕获更加确切。

在实际操作中,如果我们在Lambda体内或匿名内部类中要对外部的某些量进行操作,那么这种限制也是很容易被规避,因为即使数组是final的(即该数组不能再指向其他数组对象),里面的值依旧可变。

所以我们只要将那个需要被操作的外部变量包装进一个数组即可:

复制代码

final double[] a = {3.141592};
final double[] b = {3.141592};

DoubleUnaryOperator anotherDoubleUnaryOperator = x -> {
    a[0] = 2; // COOL
    b[0] = 3; // ALSO COOL
    return 0.0;
};

复制代码

也算是一个小技巧。

 

 

 

二.匿名内部类的实现

public static void main(String[] args) {
		//不用写Runnable接口的匿名内部类
		new Thread(()->System.out.println(11)).start();
		//等于
		new Thread(new Runnable() {
			@Override
			public void run() {
				System.out.println(1);
			}
		}).start();
	}

三.和函数引用配合使用

 

/*
 * 测试函数引用
 */
public class Test2 {
	public static void main(String[] args) {
		// 1.常规实现 匿名内部类
		demo1(new A() {
			@Override
			public double f(double a, double b) {
				return a * b;
			}
		});
		//2.实现  -->a,b 类型被省去,return被省去
		demo1((a,b)->a*b);
		
		
		//函数引用
		//在A接口的匿名内部类中,调用Test2.demo(a, b)
		demo1(new A() {
			@Override
			public double f(double a, double b) {
				return Test2.demo2(a, b);
			}
		});
		
		demo1(Test2::demo2);
		
		
	}
	

	static void demo1(A a) {
		double r = a.f(3.14, 23);
		System.out.println(r);
	}
	static double demo2(double a,double b) {
		return a*b;
	}
}



package 示例;
/*
 * 我是一个只有一个方法的接口
 */
public interface A {
	  double f(double a,double b);
}

结论:有趣,但可读性差,可读性更差的是函数编程

你可能感兴趣的:(java基础)