TheBigBlue 2020-02-13
定义:通过该类型可以有效的避免空指针异常
def func(a: Double, b: Double): Option[Double] = { if (b != 0) { //没错的情况下 返回值用Some函数包起来 Some(a / b) } else { //无值 返回None None } } def main(args: Array[String]): Unit = { var a = func(2.0, 2.0) println(a) //查看返回值的方法 println(a.getOrElse(0.0)) //Some(1.0) //1.0 }
格式:val 函数名:PartialFunction[参数类型,返回值类型]={
case 1 => "..."
case 2 => "..."
case _ => "其他"
}
val cmm: PartialFunction[Int, String] = { case 1 => "1" case 2 => "2" case _ => "其他" } println(cmm(1)) println(cmm(2)) println(cmm(3)) //1 //2 //其他
//把偏函数作为其他方法的参数传入,类比函数化编程 var li = 1.to(10).toList //需求:将列表的每一个元素转换成属于他的范围 var m = li.map { case m if m >= 1 && m <= 3 => "[1-3]" case m if m >= 4 && m <= 7 => "[4-7]" case m if m > 7 => "[7-*]" } println(m) //List([1-3], [1-3], [1-3], [4-7], [4-7], [4-7], [4-7], [7-*], [7-*], [7-*])
格式:var 变量名:Regex =""" 规则""".r
//正则表达式 var r: Regex = """+\..+""".r var x = "" //该方法返回一个迭代器 var res = r.findAllMatchIn(x) print(res.next()) //
格式:try{代码}
catch{
//异常处理
case ex:Exception【错误类型】 => "返回值"
...
}
finally{最后都会执行的代码}
try { 2 / 0 } catch { case ex: ArithmeticException => println("除数不可以是0") } finally { println("无论如何最后我都会执行的") } //除数不可以是0 //无论如何最后我都会执行的
主动抛出异常:throw new Exception("这是我自己主动抛出的异常")
定义:把对象相关属性,通过${} 提取,样例类实现了提取器,而普通的类没有提取器之说
本质:就是把一个对象的属性 获取出来 通过元祖的形式返回
case class Person(var name: String) def main(args: Array[String]): Unit = { var a: Any = Person("cmx") a match { case Person(name) => println(s"${name}") } //结果 //cmx }
自定义提取器:提取器只能定义在伴生对象中,且于apply方法成对出现
注意:提取器的 返回值是多个的话用元组括起来,只有一个的话直接返回即可
class Person(var name: String) object Person { //快速创建对象的方法 def apply(name: String) = { new Person(name) } //提取器 :参数类型:与类保持一致,返回值使用Option,避免空指针 def unapply(arg: Person): Option[String] = { if (arg != null) { Some(arg.name) } else { None } } } class User(var id: Int, var name: String) object User { def apply(id: Int, name: String) = new User(id, name) //完整写法 //def unapply(arg: User): Option[(Int, String)] //简写 利用类型推导 def unapply(arg: User) = { var res = (arg.id, arg.name) Some(res) } } def main(args: Array[String]): Unit = { //定义时使用Any 防止模式匹配时不知是那个类型 var a: Any = Person("cmx") var b: Any = User(1, "cmx01") a match { case Person(name) => println(s"${name}") case User(id, name) => println(s"${id}${name}") } //cmx b match { case Person(name) => println(s"${name}") case User(id, name) => println(s"${id}${name}") } //1cmx01 }
1.泛型类:可以根据需要,随意改变属性的类型
class Cmx[T](var name: T) { var age: T = _ } def main(args: Array[String]): Unit = { var a = new Cmx[String]("cmx") println(a.name.getClass) //class java.lang.String var b = new Cmx[Int](123) println(b.name.getClass) //int //样例类也可以 case class Cmx01[T](var name: T) var c = Cmx01[Double](10.0) println(c.name.getClass) //double }
2.泛型方法
def func[T](name: T) = { println(name) } def func2[T](a: Array[T]) = { a.foreach(println(_)) } def main(args: Array[String]): Unit = { func[String]("cmx") func[Int](1) //cmx //1 //赋值时[T]的类型 决定后面参数的类型 二者必须保持一致 func2[String](Array("1", "2")) func2[Int](Array(1, 2, 3)) }
3.泛型的上下界
上界:[T <: 类型] 或者是这个类型 或者 是这个类型的子类
下界:[T >: 类型] 或者是这个类型 或者 是这个类型父亲
class Cmx class Cmx01 extends Cmx //下界 def func[T >: Cmx01](name: T) = println(name) //上界 def func1[T <: Cmx01](name: T) = println(name) def main(args: Array[String]): Unit = { //下界演示:只要时Cmx01或者其父类均可,但是依旧要保持前后的二者类型相同 func[Cmx](new Cmx) func[Cmx01](new Cmx01) // // //上界演示 func1[Cmx](new Cmx) //直接报错 ,意为最大就是Cmx01 ,因为它是上界 //Error:(26, 10) type arguments [cmm_test.test2.Cmx] do not conform to method func1‘s type parameter bounds [T <: cmm_test.test2.Cmx01] func1[Cmx01](new Cmx01) //
定义:柯里化(Currying) 将原来接受多个参数的方法转换为多个只接受一个参数的方法列表
格式案例:
def test(x:Int,y:Int):Unit = { println(x+y) } //演变成单个参数的列表 def test(x:Int)(y:Int):Unit = { println(x+y) } test(1)(2)
//格式:参数列表放在前面,后面的第二个参数是一个函数格式(函数名:(参数类型#与前面的类型保持一致)=>返回值类型) def test(x: Int)(fun1: (Int) => Int) = { fun1(x) } def main(args: Array[String]): Unit = { //借用函数编程 调用函数 println(test(1)(_ + 11)) //12 }
定义:为原本定义好的类,增加新的功能
//定义方法阶段:构造器的参数 类型必须时String 因为你要添加这个原始类的功能 class Text(var s: String) { //这个方法就是我们要添加String类的新方法,名字即为方法 //方法自定义:参数可写可不写 扩展性大 def func() = { println(s"${s}=>cmx") } } //通过implicit 实装与String //关键字imolicit 后的方法里的参数类型也要是String,后面的实例化 必须是定义阶段的类 implicit def func2(e: String) = new Text(e) def main(args: Array[String]): Unit = { //测试 var a: String = "hhh" a.func() //hhh=>cmx }
//自定义的一个类 参数类型需是要添加方法的类 class RichFile(val f: File) { def read() = { //scala中的io操作读取文件并转化成字符串 Source.fromFile(f).mkString } } //隐式转换实装 implicit 关键字 函数名 随意 参数名随意 参数类型 :要添加方法的类 //函数体:new 前面定义过的类然后将参数放进去 implicit def Cmx(f: File) = new RichFile(f) def main(args: Array[String]): Unit = { //文件自定义 路径要写对 盘符不区分大小写 //实例化File 对象 这时该对象就可以调用read的方法了 var f = new File("e:/1.txt") val str = f.read() println(str) //ssss }