Scala---样例类+隐式转换

样例类(case classes)

1、概念理解

使用了case关键字的类定义就是样例类(case classes),样例类是种特殊的类。实现了类构造参数的getter方法(构造参数默认被声明为val),当构造参数是声明为var类型的,它将帮你实现setter和getter方法。

  • 样例类默认帮你实现了toString,equals,copy和hashCode等方法。
  • 样例类可以new, 也可以不用new

2、例子:结合模式匹配的代码

1.case class Person1(name:String,age:Int)
2.
3.object Lesson_CaseClass {
4.  def main(args: Array[String]): Unit = {
5.    val p1 = new Person1("zhangsan",10)
6.    val p2 = Person1("lisi",20)
7.    val p3 = Person1("wangwu",30)
8.
9.    val list = List(p1,p2,p3)
10.    list.foreach { x => {
11.       x match {
12.          case Person1("zhangsan",10) => println("zhangsan")
13.          case Person1("lisi",20) => println("lisi")
14.          case _ => println("no match")
15.       }
16.    } }
17.
18.  }
19.}

隐式转换

隐式转换是在Scala编译器进行类型匹配时,如果找不到合适的类型,那么隐式转换会让编译器在作用范围内自动推导出来合适的类型。

1、隐式值与隐式参数

隐式值是指在定义参数时前面加上implicit。隐式参数是指在定义方法时,方法中的部分参数是由implicit修饰【必须使用柯里化的方式,将隐式参数写在后面的括号中】。隐式转换作用就是:当调用方法时,不必手动传入方法中的隐式参数,Scala会自动在作用域范围内寻找隐式值自动传入。

隐式值和隐式参数注意:

1). 同类型的参数的隐式值只能在作用域内出现一次,同一个作用域内不能定义多个类型一样的隐式值。

2). implicit 关键字必须放在隐式参数定义的开头

3). 一个方法只有一个参数是隐式转换参数时,那么可以直接定义implicit关键字修饰的参数,调用时直接创建类型不传入参数即可。

4). 一个方法如果有多个参数,要实现部分参数的隐式转换,必须使用柯里化这种方式,隐式关键字出现在后面,只能出现一次

1.object Lesson_ImplicitValue {
2.
3.  def Student(age:Int)(implicit name:String,i:Int)= {
4.    println( s"student :$name ,age = $age ,score = $i")
5.  }
6.  def Teacher(implicit name:String) ={
7.    println(s"teacher name is = $name")
8.  }
9.
10.  def main(args: Array[String]): Unit = {
11.    implicit val zs = "zhangsan"
12.    implicit val sr = 100
13.
14.    Student(18)
15.    Teacher
16.  }
17.}

2、隐式转换函数

隐式转换函数是使用关键字implicit修饰的方法。当Scala运行时,假设如果A类型变量调用了method()这个方法,发现A类型的变量没有method()方法,而B类型有此method()方法,会在作用域中寻找有没有隐式转换函数将A类型转换成B类型,如果有隐式转换函数,那么A类型就可以调用method()这个方法。

隐式转换函数注意:隐式转换函数只与函数的参数类型和返回类型有关,与函数名称无关,所以作用域内不能有相同的参数类型和返回类型的不同名称隐式转换函数。

1.class Animal(name:String){
2.  def canFly(): Unit ={
3.    println(s"$name can fly...")
4.  }
5.}
6.class Rabbit(xname:String){
7.  val name = xname
8.}
9.object Lesson_ImplicitFunction {
10.
11.  implicit def rabbitToAnimal(rabbit:Rabbit):Animal = {
12.     new Animal(rabbit.name)
13.  }
14.
15.  def main(args: Array[String]): Unit = {
16.    val rabbit = new Rabbit("RABBIT")
17.    rabbit.canFly()
18.  }
19.}

3、隐式类

使用implicit关键字修饰的类就是隐式类。若一个变量A没有某些方法或者某些变量时,而这个变量A可以调用某些方法或者某些变量时,可以定义一个隐式类,隐式类中定义这些方法或者变量,隐式类中传入A即可。

隐式类注意:

1).隐式类必须定义在类,包对象,伴生对象中。

2).隐式类的构造必须只有一个参数,同一个类,包对象,伴生对象中不能出现同类型构造的隐式类。

1.class Rabbit(s:String){
2.  val name = s
3.}
4.
5.object Lesson_ImplicitClass {
6.
7.  implicit class Animal(rabbit:Rabbit){
8.    val tp = "Animal"
9.    def canFly() ={
10.      println(rabbit.name +" can fly...")
11.    }
12.  }
13.
14.  def main(args: Array[String]): Unit = {
15.    val rabbit = new Rabbit("rabbit")
16.    rabbit.canFly()
17.    println(rabbit.tp)
18.  }
19.}
相关推荐
清风fu杨柳3 分钟前
centos7 arm版本编译qt5.6.3详细说明
开发语言·arm开发·qt
醉颜凉5 分钟前
【NOIP提高组】潜伏者
java·c语言·开发语言·c++·算法
_小柏_8 分钟前
C/C++基础知识复习(20)
开发语言
程序员小明z17 分钟前
基于Java的药店管理系统
java·开发语言·spring boot·毕业设计·毕设
夜色呦28 分钟前
现代电商解决方案:Spring Boot框架实践
数据库·spring boot·后端
爱敲代码的小冰36 分钟前
spring boot 请求
java·spring boot·后端
我是哈哈hh1 小时前
HTML5和CSS3的进阶_HTML5和CSS3的新增特性
开发语言·前端·css·html·css3·html5·web
Dontla1 小时前
Rust泛型系统类型推导原理(Rust类型推导、泛型类型推导、泛型推导)为什么在某些情况必须手动添加泛型特征约束?(泛型trait约束)
开发语言·算法·rust
java小吕布2 小时前
Java中的排序算法:探索与比较
java·后端·算法·排序算法
Neophyte06082 小时前
C++算法练习-day40——617.合并二叉树
开发语言·c++·算法