Scala语言中的隐式转换是一个十分强大的语言特性,主要可以起到两个作用:
一.自动进行某些数据类型的隐式转换
String类型是不能自动转换为Int类型的,所以当给一个Int类型的变量或常量赋予String类型的值时编译器将报错。所以,一下语句是错误的。
val x: Int = "100"
如果需要将一个字符串类型的整形数值赋给Int,比如使用String.toInt方法,例如:
val x: Int = "100".toInt
如果想让字符串自动转换为整形,就可以使用隐式转换。可以定义如下函数。
implicit def strToInt(str: String) = str.toInt
这时你再对Int类型的变量赋值字符串时,字符串就会自动转换为Int。
scala> val x:Int = "00" x: Int = 100
如果你此时定义一个两数相加的函数
def add(x: Int, y: Int) = x + y
就可以达到这种效果:
scala> add("100", 200) res1: Int = 300
隐式转换有一定的使用规则,比较重要的有2个。
1.按照《Scala编程》这本书中所说:插入的隐式转换必须以单一标识符的形式处于作用域中,或与转换的源或目标类型关联在一起。Scala编译器将仅考虑处于作用域之内的隐式转换。
简而言之,就是在使用隐式转换之前,需要用import把隐式转换引用到当前的作用域里或者就在作用域里定义隐式转换。除了隐式转换被引入进当前作用域之外,还有一种方式可以使用隐式转换,就是编译器会在源类型或者期望的伴生对象中寻找隐式定义。
2.无歧义规则:隐式转换只能在无其他可用转换的前提下才能操作。如果在同一作用域里,对同一源类型定义一个以上的隐式转换函数,如果多种隐式转换函数都可以匹配,那么编译器将报错,所以在使用时请移除不必要的隐式定义。
二.隐式参数
柯里化函数会有多个参数列表,当希望对某个参数列表采用默认参数时,可以使用implicit提供的隐式参数功能。做法是在需要自动填充的参数列表最开端加上implicit,然后在定义域内定义需要填充的默认参数值常量,并在常量的定义之前声明implicit。
视界
当有如下定义时
class Container[A <% Int] { def addIt(x: A) = 123 + x }
表示A类型必须可视为Int。简单的说,就是需要有一个转换函数,可以自动的将A类型,转换为Int类型,如果没有这样的转换函数,可以使用implicit定义。
写一个类测试一下Scala中的隐式转换的用法:
class Fraction(n: Int, d: Int) { // def den = d private val den = d; // def num = n 类参数定义为方法或字段都可以 private val num = n; // 定义乘法 def *(other: Fraction) = Fraction(other.num * this.num, other.den * this.den) // 重写toString override def toString() = s"$num / $den" } //伴生对象 object Fraction { // implicit隐转 方法名无关可以随意改,自动调用 implicit def int2Fraction(n: Int) = Fraction(n, 1) def apply(n: Int, d: Int) = { new Fraction(n, d) } def unapply(frac: Fraction) = if (frac.den == 0) None else Some((frac.num, frac.den)) } object TestFrac extends App{ // 3 隐式调用了int2Fraction方法被转化为一个Fraction对象Fraction(3,1) val result = 3 * Fraction(4,5) // 也可以显示调用 val result2 = Fraction.int2Fraction(5) * Fraction(3,4) println(result) // unapply val Fraction(num,den) = result println(num,den) }
以上就是本文的全部内容,希望对大家的学习有所帮助,也希望大家多多支持小牛知识库。
本文向大家介绍总结Javascript中的隐式类型转换,包括了总结Javascript中的隐式类型转换的使用技巧和注意事项,需要的朋友参考一下 JavaScript的数据类型分为六种,分别为null,undefined,boolean,string,number,object。object是引用类型,其它的五种是基本类型或者是原始类型。 比如像是Number() ,还是parseInt() 、pa
本文向大家介绍有趣的JavaScript隐式类型转换操作实例分析,包括了有趣的JavaScript隐式类型转换操作实例分析的使用技巧和注意事项,需要的朋友参考一下 本文实例讲述了JavaScript隐式类型转换操作。分享给大家供大家参考,具体如下: JavaScript的数据类型是非常弱的(不然不会叫它做弱类型语言了)!在使用算术运算符时,运算符两边的数据类型可以是任意的,比如,一个字符串可以和数
本文向大家介绍JavaScript强制类型转换和隐式类型转换操作示例,包括了JavaScript强制类型转换和隐式类型转换操作示例的使用技巧和注意事项,需要的朋友参考一下 本文实例讲述了JavaScript强制类型转换和隐式类型转换。分享给大家供大家参考,具体如下: 在JavaScript中声明变量不需指定类型, 对变量赋值也没有类型检查,同时JavaScript允许隐式类型转换。这些特征说明Ja
本文向大家介绍请你来说一说C++中的隐式类型转换?相关面试题,主要包含被问及请你来说一说C++中的隐式类型转换?时的应答技巧和注意事项,需要的朋友参考一下 首先,对于内置类型,低精度的变量给高精度变量赋值会发生隐式类型转换,其次,对于只存在单个参数的构造函数的对象构造来说,函数调用可以直接使用该参数传入,编译器会自动调用其构造函数生成临时对象。
我在学习Scala playframework教程时遇到了一段令我迷惑不解的代码: 于是我决定调查一下,偶然发现了这个帖子。
本文向大家介绍Javascript的typeof返回哪些数据类型;列举3种强制类型转换和2中隐式类型转换相关面试题,主要包含被问及Javascript的typeof返回哪些数据类型;列举3种强制类型转换和2中隐式类型转换时的应答技巧和注意事项,需要的朋友参考一下 1)返回数据类型 undefined string boolean number symbol(ES6) Object Function