Lamda表达式学习

来源:互联网 发布:熊片数据库kfb 编辑:程序博客网 时间:2024/06/05 23:06

Lamda表达式学习

参考:

http://blog.csdn.net/xmxkf/article/details/51532028#3-函数式接口functional-interfaces

http://colobu.com/2014/10/28/secrets-of-java-8-functional-interface/

http://www.cnblogs.com/ownraul/p/5551545.html

 

简介:

Lamda表达式是java SE 8 中出来的。主要针对的是由于内部类带来的冗余语法的问题。

Eg:

textView.setOnClickListener(newView.OnClickListener(){

   @Override

   publicvoid onClick(View v) {

       Toast.makeText(getApplicationContext(), "helloLambda", Toast.LENGTH_LONG).show();

   }

});

经过处理之后为:

textView.setOnClickListener(

v -> Toast.makeText(getApplicationContext(),"Lambda", Toast.LENGTH_LONG).show());

因此,我们引入lamda语法主要要解决匿名内部类的:

1、      语法过于冗余

2、      类型载入和实例创建语义不够灵活(也就是泛型问题)

3、      减少了无法捕获非final的局部变量的影响

安卓中引入lamda

参看参考文章

lamda主要使用的规则

它可以替代的地方必须是“函数式接口”

函数式接口代表的一种契约,一种对某个特定函数类型的契约。在它出现的地方,实际期望一个符合契约要求的函数。 Lambda表达式不能脱离上下文而存在,它必须要有一个明确的目标类型,而这个目标类型就是某个函数式接口:SAM类型的接口(Single Abstract Method)

早期的函数式接口:

l  java.lang.Runnable

l  java.util.concurrent.Callable

l  java.security.PrivilegedAction

l  java.util.Comparator

l  java.io.FileFilter

l  java.nio.file.PathMatcher

l  java.lang.reflect.InvocationHandler

l  java.beans.PropertyChangeListener

l  java.awt.event.ActionListener

l  javax.swing.event.ChangeListener

jdk8新增的函数式接口:

l  Predicate -- 传入一个参数,返回一个bool结果,方法为boolean test(T t)

l  Consumer -- 传入一个参数,无返回值,纯消费。方法为void accept(T t)

l  Function -- 传入一个参数,返回一个结果,方法为R apply(T t)

l  Supplier -- 无参数传入,返回一个结果,方法为T get()

自定义的函数式接口:

@FunctionalInterface

interface Converter<F, T> {

    Tconvert(F from);

}

使用:

Converter<String, Integer> converter= (from) -> Integer.valueOf(from);

Integer converted =converter.convert("123");

Lamda语法:

ambda表达式的语法由参数列表箭头符号->函数体组成

 

无参数:

Interface3 in31 = ()-> {

   Log.v(TAG, "吃饭了吗");

    returntrue;

};

一个参数

Interface2 in21 = name->{

    Log.v(TAG,"有这个人吗?");

    Log.v(TAG,"没有啊");

    returnfalse;

};

多个参数

Interface1 in2 = (name, age, addr) ->{

    Log.v(TAG,"有这个人吗?");

    Log.v(TAG,"没有啊");

    returnfalse;

};

多个参数并赋予类型:

private void lambda3(){

   Interface1 in1 = (String name, int age, String addr)->{

       Log.v(TAG, "有这个人吗?");

       Log.v(TAG, "没有啊");

       return false;

   };

}

在使用lamda需要注意的问题:

1、它不会从父类(supertype)中继承任何变量名,也不会引入一个新的作用域。lambda表达式函数体里面的变量和它外部环境的变量具有相同的语义。

class Activity{
button.setOnClickListener(v->{this.finish();})
}
this代表的是Activity对象,而不是OnClickListener对象;
如果你写成下面的样子:
class Activity{
button.setOnClickListener(new OnClickListener(View v){
this.xxx()
});
}
这个this就是指的OnClickListener这个匿名对象,如果你要用Activity对象,必须用Activity.this

2、不必再像内部内一样在用到外部的变量时还要转化为final才能用。

 

 

原创粉丝点击