Kotlin对象表达式要点与Lambda表达式
Kotlin对象表达式要点揭密:
在上一次https://www.cnblogs.com/webor2006/p/11352421.html中学习了Kotlin的对象表达式,它主要是解决Java中匿名内部类的问题,这次继续对它进行学习,在上一次的示例中,我们定义了一个不继承任何类或实现任何接口的对象表达式,回忆如:

当时说该代码看似简单,其实里面有一些很隐晦的东东接下来阐述一下:

嗯,很简单,那接下来改一个东东就会让你觉得难以理解了:


报异常了。。这是为啥呢?这就是之前提出的“隐晦”处了,这里会涉及到对象表达式的一些注意事项及要点,下面来说明一下:
1、匿名对象只能在局部变量范围内或者被private修饰的成员变量范围内才能被识别出来其真正的类型,其中“被识别出真正的类型”的含义是指能正常的调用匿名内部类中的方法或成员变量,比如我们之前定义在局部变量范围的匿名对象:

所以它是能被正常识别出真正类型的,而目前咱们新定义的这个如果是被private修饰的话也是能被识别真正类型:

而如果将private关键字去掉之后,在Kotlin中默认在类中的访问级别就会变为public了,所以该匿名对象是不能被识别出真正的类型的,所以也就如我们所看到的报错了。
2、如果将匿名对象当做一个public方法的返回类型或是public属性的类型,那么该方法或是属性的真正类型就是该匿名对象所声明的父类型,如果没有声明任何父类型,那么其类型就是Any;在这处情况下,匿名对象中所声明的任何成员都是无法访问的。
回到咱们的这个程序理解一下这句话,也就是如果我们当private关键字去掉之后,会变为public属性类型了,此时它真正的类型就是该匿名对象的父类型,而根据“如果没有声明任何父类型,那么其类型就是Any”,也就是说:

为了进一步论证这个理论,咱们可以将myObject的类型打出来:

另外打印类型还有另外一种写法,了解一下:

接下来再来定义一个类进一步再来感受这个对象表达式的注意事项:

我们知道对于Java的匿名内部类中的方法想要访问外层类的变量,该外层类的变量一定得要声明为final才行,但是对于Kotlin的对象表达式而言是没有这个限制的,下面来用程序验证一下:

实际案例:
我们知道在Java的GUI编程中就会用到很多的匿名内部类,因为要监听控件的事件,下面则先用Java原滋原味的展现一下,然后稍后再用Kotlin的对象表达式将其改造,最后再来做一个对比,如下:
package com.kotlin.test3; import javax.swing.*;
import java.awt.event.WindowEvent;
import java.awt.event.WindowListener; public class JFrameTest {
public static void main(String[] args) {
JFrame jFrame = new JFrame("My JFrame");
JButton jButton = new JButton("My JButton"); jFrame.addWindowListener(new WindowListener() {
@Override
public void windowOpened(WindowEvent e) {
System.out.println("windowOpened");
} @Override
public void windowClosing(WindowEvent e) {
System.out.println("windowClosing");
} @Override
public void windowClosed(WindowEvent e) { } @Override
public void windowIconified(WindowEvent e) { } @Override
public void windowDeiconified(WindowEvent e) { } @Override
public void windowActivated(WindowEvent e) {
System.out.println("windowActivated");
} @Override
public void windowDeactivated(WindowEvent e) { }
}); jFrame.add(jButton);
jFrame.pack();
jFrame.setVisible(true);
jFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
}
}
然后运行:

然后咱们可以给Button增加一个点击事件:

还可以将其改为Lambda表达式,如下:

很简单的代码,接下来咱们用Kotlin的方式来实现同样的功能:

好,继续:

好,接下来是来设置可见性,在Java中是这样写的:

而在Kotlin中如果我们敲setVisible会自动匹配其它的一个名称,如下:

会自动变为isVisible,也就是Kotlin中推荐是用属性的方式来代替Java中的set和get方法,如下:

当我们点击查看时,自动会链接到setVisible()方法中:

其中还有一个小细节需要注意,其实在Window中的属性名不是isVisible,而是:

这也就说明了,对于boolean类型的变量,Kotlin会自动将其翻译成is开头的,好程序继续:

接下来给按钮增加点击事件:

Kotlin Lambda表达式:
关于Java的Lambda表达式已经很清楚了,也就是如果对象是Java函数式接口的一个实例(既只拥有一个抽象方法的接口),那么可以通过Lambda表达式来调用,其中Lambda表达式前面加上接口的类型。下面来对上面的Button的点击事件改成Kotlin的Lambda表达式,看跟Java的Lambda表达式有啥不一样:

但是!!其实还可以简化,从上面可以看出“ActionListener”被IDE标灰了,看一下它的提示:

其实这个ActionListener可以由Kotlin的编译推断出来,因为addActionListener方法接收的参数类型就是ActionListener,所以:

最后再来做个小实现:

Kotlin对象表达式要点与Lambda表达式的更多相关文章
- C#在泛型类中,通过表达式树构造lambda表达式
场景 最近对爬虫的数据库架构做调整,需要将数据迁移到MongoDB上去,需要重新实现一个针对MongoDB的Dao泛型类,好吧,动手开工,当实现删除操作的时候问题来了. 我们的删除操作定义如下:voi ...
- Kotlin语法(函数和lambda表达式)
三.函数和lambda表达式 1. 函数声明 fun double(x: Int): Int { } 函数参数是用 Pascal 符号定义的 name:type.参数之间用逗号隔开,每个参数必须指明类 ...
- C# LINQ查询表达式用法对应Lambda表达式
C#编程语言非常优美,我个人还是非常赞同的.特别是在学习一段时间C#后发现确实在它的语法和美观度来说确实要比其它编程语言强一些(也可能是由于VS编译器的加持)用起来非常舒服,而且对于C#我觉得他最优美 ...
- 委托、 Lambda表达式和事件——Lambda表达式
/* * 由SharpDevelop创建. * 用户: David Huang * 日期: 2015/7/30 * 时间: 16:32 */ using System; namespace Lambd ...
- C# Lambda表达式和linq表达式 之 匿名对象查询接收
很多小伙伴都用过Lambda表达式和linq表达式,用起来也得心应手,但是有的小伙伴 对匿名对象的查询与接收比较迷茫,(没有定义相应的实体),怎么在where()里面进行 条件筛选呢?常规用法我就不说 ...
- 【C++】C++中的lambda表达式和函数对象
目录结构: contents structure [-] lambda表达式 lambda c++14新特性 lambda捕捉表达式 泛型lambda表达式 函数对象 函数适配器 绑定器(binder ...
- 《疯狂Kotlin讲义》读书笔记6——函数和Lambda表达式
函数和Lambda表达式 Kotlin融合了面向过程语言和面向对象语言的特征,相比于Java,它增加了对函数式编程的支持,支持定义函数.调用函数.相比于C语言,Kotlin支持局部函数(Lambda表 ...
- 1.1 为什么要使用lambda 表达式
第1章 lambda 表达式 1.1 为什么要使用lambda 表达式 1.2 lambda 表达式的语法 1.3 函数式接口 1.4 方法引用 1.5 构造器引用 1.6 变量作用域 1.7 默认方 ...
- 深入学习C#匿名函数、委托、Lambda表达式、表达式树类型——Expression tree types
匿名函数 匿名函数(Anonymous Function)是表示“内联”方法定义的表达式.匿名函数本身及其内部没有值或者类型,但是可以转换为兼容的委托或者表达式树类型(了解详情).匿名函数转换的计算取 ...
随机推荐
- DevOps - DevOps精要 - 变革
特别说明 本文是已读书籍的学习笔记和内容摘要,原文内容有少部分改动,并添加一些相关信息,但总体不影响原文表达. <DevOps入门与实践> :本书结合实例详细介绍了在开发现场引入DevOp ...
- 常用的python的内置库或者第三方库
内置库:re,json,time,random,sys,os, 第三方库:转载: https://www.cnblogs.com/jiangchunsheng/p/9275881.htmlReques ...
- QT 安装 配置过程
QT, QT creator的安装,环境配置: 需要根据这个连接重新梳理一遍:https://blog.csdn.net/win_turn/article/details/50465127 1)一种方 ...
- [转帖]GNU, Free Software and Open Source 自由软件与开源软件
GNU, Free Software and Open Source 自由软件与开源软件 https://blog.csdn.net/icycolawater/article/details/7792 ...
- unexpected end of file while looking for precompiled headerdirective Add directive to 'stdafx.h' or rebuild precompiled header错误
解决方式: 项目工程右键->propertity(属性),选择不用于预编译头 原因: C++的编译过程如下: 当头文件很多时,预编译过程需要耗费大量时间,为了减少重复编译的次数,C和C++提供了 ...
- python网课自动刷课程序-------selenium+chromedriver
python的强大之处就在于有许多已经写好的功能库提供,这些库强大且易用,对于写一些有特定功能的小程序十分方便. 现在就用pyhton的selenium+谷歌游览器写一个可以自动刷课的程序,以智慧树上 ...
- 【LEETCODE】39、第561题 Array Partition I
package y2019.Algorithm.array; /** * @ProjectName: cutter-point * @Package: y2019.Algorithm.array * ...
- 12.1 Mapping手动创建
只能在index里的field不存在的时候,才能指定新field的数据类型,field有数据后,就不能再修改field的类型了 可创建的类型如下: integer double date text/s ...
- jenkins配置Webhook-gitlab
1.Jenkins 安装完成以后,首先我们在Jenkins中需要安装一下,Gitlab Hook Plugin,GitLab Plugin,Gitlab Authentication plugin插件 ...
- 浮动和渐变色,定位position,元素的层叠顺序
浮动: float 是我们网页布局的一种 浮动 可以有 left 左浮动 right 右浮动 两种 浮动的特点: 脱离正常的文档流,原本的空间不占据,浮动的标签都具有块级标签的一些特点,可以手动设置宽 ...