文档章节

Scala Implicit Parameters

秋风醉了
 秋风醉了
发布于 2015/04/28 17:34
字数 600
阅读 76
收藏 0

Scala Implicit Parameters

如果定义函数时,标明某一参数为implicit,则这个参数是隐式参数。看起来与缺省参数(Default Parameters)类似,调用者不必在调用时指定该参数。

但是就实际运行机制而言,隐式参数与缺省参数是完全不一样的。缺省参数是函数定义方设定了一个缺省值,在调用者没有指明时将使用该缺省值。 隐式参数则不同,最终是会由调用方指定参数值,只是不一定在调用的语句里指定而已。编译器在发现缺少隐式参数时,会在程序范围内寻找符合类型的隐式值,如果找不到则编译会失败。

如下代码,

abstract class Logger {
  def log(s: String)
}

class FileLogger extends Logger {
  def log(s: String) {
    println("Log in file: " + s)
  }
}

class StdoutLogger extends Logger {
  def log(s: String) {
    println("Stdout: " + s)
  }
}

def Add(a: Int, b: Int)(implicit logger: Logger) {
  val sum = a + b
  logger.log("%d + %d = %d".format(a, b, sum))
}

implicit val log = new FileLogger

Add(1, 2)
Add(2, 3)(new StdoutLogger) //you may do it explicitly

运行并输出,

C:\WorkSpace6-scala\scala-train\src\com\usoft>scala implicit_parameter.scala

Log in file: 1 + 2 = 3

Stdout: 2 + 3 = 5

如果上述代码没有implicit val log = new FileLogger这一句,在代码范围内也没有其他的Logger类型的implicit值,编译器会报错:

could not find implicit value for parameter logger: com.scalass.examples.blog.ImplicitParameters.Logger

反之,如果能找到Logger类型的隐式值,编译器会将该隐式值作为参数传递过去。

与隐式转换一样,你也可以选择显示的传递隐式参数,实际上编译器就是这样做的,在程序上下文找到符合类型要求的隐式值,将它显示的作为参数传递。 也与隐式转换一样,隐式值的名称对编译器并无影响,只要类型符合即可,但是为了可读性,建议赋予它合适的名称。

到这里可能你会有些想法了,其实同样的功能可能可以由依赖注入等方式实现。在使用依赖注入,或是继承等方式能实现的情况下,我们不建议使用隐式转换或隐式参数。 因为其他的方式,代码结构可能会更清晰,而过多的使用隐式转换或隐式参数常常会让读者摸不着头脑。

============END============

本文转载自:http://meetfp.com/zh/blog/implicit-parameters

共有 人打赏支持
秋风醉了
粉丝 239
博文 572
码字总数 416654
作品 0
朝阳
程序员
私信 提问
IntelliJ Scala Plugin 1.3 EAP 1.2.67 发布

IntelliJ Scala Plugin 1.3 EAP 1.2.67 发布,此版本现已提供下载:http://download.jetbrains.com/scala/scala-intellij-bin-1.2.67.1.EAP.zip,包括大量改进: Moncole 支持 Unused impor......

oschina
2015/01/20
1K
1
Scala 的下一代编译器--Dotty

Dotty 是 Scala 的下一代编译器,也是 Scala 的新语言概念和编译器技术研究平台。 具有以下特性: Union, intersection and literal singleton types Implemented Trait parameters Impleme...

匿名
2017/06/02
1K
3
Scala Plugin 1.3 for IntelliJ IDEA 14.0.3 发布

Scala Plugin 1.3 for IntelliJ IDEA 14.0.3 发布,此版本更新内容如下: 调试器改进 Мariables from the outer scopes are visible in the Variables tab now: there is no need to evalua......

oschina
2015/01/30
1K
1
Scala implicit implicit基本含义

Scala implicit implicit基本含义 在Scala中有一个关键字是implicit, 之前一直不知道这个货是干什么的,今天整理了一下。 我们先来看一个例子: def display(input:String):Unit = println...

泳泳啊泳泳
01/07
0
0
Scala学习笔记(4):关于String

Scala并没有定义自己的String类型,而是直接借用了Java中的String,所以如果你定义一个String类型的值: val str = "hello" 返回的值的类型直接就是java.lang.String。然而,我们知道在Scala...

chengyao2
2013/05/14
0
0

没有更多内容

加载失败,请刷新页面

加载更多

如何在Chrome浏览器中启动deviceready事件(尝试调试phonegap项目)?

我正在开发PhoneGap应用程序,我希望能够在Chrome中调试它,而不是在电话上调试。但是,我在onGetReady()函数中初始化我的代码,该函数在PhoneGap触发“deviceready”事件时触发。由于Chr...

kisshua
24分钟前
1
0
支付宝客户端架构分析:自动化日志收集及分析

摘要: 《支付宝客户端架构解析》系列将从支付宝客户端的架构设计方案入手,带领大家进一步了解支付宝在客户端架构上的迭代与优化历程。 小蚂蚁说: 《支付宝客户端架构解析》系列将从支付宝...

阿里云官方博客
27分钟前
1
0
nginx中部署vue打包后的静态文件

如何在nginx中部署静态资源就不描述了, 请看我的这篇博客 将vue脚手架项目打包后的静态文件放到nginx上, 发现有个问题, 即url上有#, 怎么去掉这个#呢. 1 项目中router的mode 路由的mode要为h...

克虏伯
45分钟前
7
0
JS容易理解错误的地方

在这端代码执行的末尾,你会不会hi变量回事函数中的hi了?你会不会认为这不是按引用传递了? 对值传递和引用传递产生质疑了? 1 var hi = {};2 function sayHello(hi) { ...

器石_
46分钟前
4
0
Java开发学习--MongoDB

之前只学过sql,第一次使用非关系型数据库。以前对于关系型数据库与非关系型数据库的概念很模糊,通过这次的学习对这两者有了一个清晰的概念。 主键 在MongoDB中,主键名叫"_id",如果在生成...

微笑向暖wx
50分钟前
4
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部