Scala零基础教学【21-40】

第24讲:Scala中SAM转换实战详解

SAM:single abstract method 单个抽象方法
 
我们想传入一个函数来指明另一个函数具体化的工作细节,但是重复的样板代码很多。
我们不关心它实现了什么接口的什么方法,只关心这个动作。比如下面的按钮点击一次,data就加1,而不关心ActionListener以及其回调方法。
那么就用隐式转换。这个后面会彻底地讲解。
 

第25讲:Scala中Curring实战详解

 
柯里化(Currying)是把接受多个参数的函数变换成接受一个单一参数(最初函数的第一个参数)的函数,并且返回接受余下的参数且返回结果的新函数的技术。
 

从数学的角度讲,这是一个对函数消元求解的过程:

def f(x:Int,y:Int)=x+y

def g(x:Int)=f(x,1)

def z=g(1)

z=2

那么z也可以写成这样:def z=(x:Int)=>(y:Int)=>x+y

例如:

def add(x:Int,y:Int)=x+y

柯里化后:

def add(x:Int)(y:Int)=x+y

实际实现是scala的语法糖,依次调用两个普通函数,第一次调用函数(x),第二次调用时使用了(x)的返回值。

def add=(x:Int)=>(y:Int)=>x+y

那么具体怎么实现柯里化呢?

假设我原始的普通函数 def add(x:Int,y:Int)=x+y

目标函数是Int=>Int=>Int (或者Int=>(Int=>Int))

大概长这样def add=(x:Int)=>(y:Int)=>x+y

抽象出来是[参数1=>参数2=>function(参数1,参数2)]
柯里化函数:
       def curry[A,B,C](f: (A, B) => C): A => (B => C) =  a => b => f(a, b)

curry: [A, B, C](f: (A, B) => C)A => (B => C)

用柯里化函数调用非柯里化函数add后:

def add(x:Int,y:Int)=x+y

def addCurry=curry(add)

addCurry: Int => (Int => Int)

测试:

addCurry(1)(2)

res10: Int = 3

 
package com.wanji.scala.function

object Curring {
  
  def main(args: Array[String]): Unit = {
    def multiple(x:Int,y:Int)=x*y
    def multipleOne(x:Int)=(y:Int)=>x*y
    println(multipleOne(6)(7))
    
    def curring(x:Int)(y:Int)=x*y
    
    println(curring(10)(10))
    val a=Array("Hello","Spark")
    val b=Array("Hello","spark")
    println(a.corresponds(b)(_.equalsIgnoreCase(_)))
    
  }
  
}

 

第28讲:Scala提取器Extractor实战详解 

第29讲:Case class和Case object代码实战解析

第30讲:模式匹配高级实战:嵌套的Case class

第31讲:Option使用和实现内幕源码揭秘

第36讲:List的partition、find、takeWhile、dropWhile、span、forall、exsists操作代码实战

val r1 = s1.takeWhile( _ < 10)
r1: List[Int] = List(1, 2, 3, 4)
takeWhile是从第一个元素开始,取满足条件的元素,直到不满足为止
 val r2 = s1.filter( _ < 10)
r2: List[Int] = List(1, 2, 3, 4, 5, 6, 7, 8)
fiter取出所有满足条件的元素
差异:
fiter取所有的满足条件的元素;
takeWhile取出从第一个开始满足条件的元素,直到遇到不满足条件的元素

    println(List(1, 2, 3, 4, 5) partition (_ % 2 ==0))
    //find:查找集合第一个符合条件的元素
    println(List(1, 2, 3, 4, 5) find (_ % 2 ==0))
    println(List(1, 2, 3, 4, 5) find (_  <=0))
    //takeWhile:着个匹配符合条件的元素 直到不符合条件 之后的元素不在判断
    println(List(1, 2, 3, 4, 5) takeWhile (_  < 4))
    //dropWhile:着个匹配去除符合条件的元素 直到不符合条件 之后的元素不在判断
    println(List(1, 2, 3, 4, 5) dropWhile (_  < 4))
    //span 着个匹配按照某种条件对数据进行分类 直到不符合条件 之后的元素不在判断
    println(List(1, 2, 3, 4, 5) span (_  < 4))


    //forall  当所有的元素满足条件时 返回true 否则返回false
    //exists  当存在(至少有一个满足)元素满足条件时 返回true 否则返回false
    def hastotallyZeroRow(m: List[List[Int]]) = m exists (row => row forall (_ == 0))
    val m= List(List(1,0,0), List(0,0,0), List(0,0,1))
    println(List(1,0,0) forall(_==0))
    println(List(0,0,0) forall(_==0))
    println(List(0,0,1) forall(_==0))
    println(hastotallyZeroRow(m))

第37讲:List的foldLeft、foldRight、sort操作代码实战

foldLeft定义:

def foldLeft[B](z: B)(op: (B, A) => B): B = {
    var result = z
    this.seq foreach (x => result = op(result, x))
    result
}

方法接受2个参数,z和op,一个是B类型的参数,一个是返回B类型的函数。

在看到这个trait其实是TraversableOnce,可迭代的集合。

 def seq: TraversableOnce[A]

比如一个val listA = List(1,2,3)

listA其实是实现了TraversableOnce这个trait的。

我们可以直接使用:

scala> listA.foldLeft(0)((sum,i)=>sum+i)
res26: Int = 6

这个里面的0其实就是z返回值是Int类型即B类型

那么可以看出op这个函数返回值也需要是Int类型

可以看出

val result = z, 这里其实就是0,x=>result=op(result, x) , sum其实也是z

其实z就是返回值,this.seq在这里就是list,对list遍历,这里执行op函数。

这里我们执行的是sum+i,就是累加了1+2+3=6

    println(List(1 to 5))
    //传递的参数在左参数
    //(10-1)-2-3-4-5=-5
    println((1 to 5).foldLeft(10)(_-_))
    //传递的参数在右参数,结果在右
    //(1-10)=-9
    //2-(-9)=11
    //3-11=-8
    //4-(-8)=12
    //5-12=-7
    println((1 to 5).foldRight(10)(_-_))
 

第38讲:List伴生对象操作方法代码实战

   //apply:根据元素构建对象
    println(List.apply(1, 2, 3))
    //make:重复构建,第一个参数个数,第二个参数是数值
    println(List.make(3, 5))
    //range:构建元素集合(1,2,3,4)
    println(List.range(1, 5))
    //rang:最后的元素是步长,(9,6,3)
    println(List.range(9, 1, -3))
    
    val zipped = "abcde".toList zip List(1, 2, 3, 4, 5)
    //List((a,1),(b,2),(c,3),(d,4),(e,5))
    println(zipped)
    //(List(a,b,c,d,e),List(1,2,3,4,5))
    println(zipped.unzip)
    //flatten:多个集合中的元素放到一个集合中
    println(List(List('a', 'b'), List('c'), List('d', 'e')).flatten)
    //多个集合拼接,类似flatten
    println(List.concat(List(), List('b'), List('c')))

    //map2:索引相同的元素操作之后放入新的集合中
    println(List.map2(List(10, 20), List(10, 10)) (_ * _))

  结果:

List(1, 2, 3)
List(5, 5, 5)
List(1, 2, 3, 4)
List(9, 6, 3)
List((a,1), (b,2), (c,3), (d,4), (e,5))
(List(a, b, c, d, e),List(1, 2, 3, 4, 5))
List(a, b, c, d, e)
List(b, c)
List(100, 200)

第39讲:ListBuffer、ArrayBuffer、Queue、Stack操作代码实战

    import scala.collection.mutable.ListBuffer
    //可变的ListBuffer,默认不可变
    val listBuffer = new ListBuffer[Int]
    listBuffer += 1
    listBuffer += 2
    println(listBuffer)
    
    import scala.collection.mutable.ArrayBuffer
    val arrayBuffer = new ArrayBuffer[Int]()
    arrayBuffer += 1
    arrayBuffer += 2
    println(arrayBuffer)
    
    val empty = Queue[Int]()
    //入队列操作 enqueue
    val queue1 = empty.enqueue(1)
    val queue2 = queue1.enqueue(List(2,3,4,5))
    println(queue2)
    //出队列操作 dequeue  def dequeue: (A, Queue[A])
    val (element, left) = queue2.dequeue
    println(element + " : " + left)
    println("immutable:"+queue2)
    println(queue2.dequeue)
    println("immutable为不可变队列:"+queue2)
    
    import scala.collection.mutable.Queue
    val queue3=Queue[Int]()
    queue3++=List(1,2,3,4,5)
    println(queue3.dequeue())
    println("mutable:"+queue3)

    val queue = Queue[String]()
    queue += "a"
    queue ++= List("b", "c")
    println(queue)
    println(queue.dequeue)
    println(queue)
    
    import scala.collection.mutable.Stack
    val stack = new Stack[Int]
    stack.push(1)
    stack.push(2)
    stack.push(3)
    //top仅仅是get操作,pop是获取加出栈
    println(stack.top)
    println(stack)
    println(stack.pop)
    println(stack)

  

第40讲:Set、Map、TreeSet、TreeMap操作代码实战

   //Set 无序集合
    val data = mutable.Set.empty[Int]
    data ++= List(1, 2, 3)
    data += 4;
    data --= List(2, 3);
    println(data)
    data += 1;
    println(data)
    data.clear
    println(data)


    val map = mutable.Map.empty[String, String]
    map("Java") = "Hadoop"
    map("Scala") = "Spark"
    println(map)
    println(map("Scala"))
    //TreeSet 有序的集合
    val treeSet = TreeSet(9, 3, 1, 8, 0, 2, 7, 4, 6, 5)  
    println("有序集合TreeSet:"+treeSet)
    val treeSetForChar = TreeSet("Spark", "Scala", "Hadoop")  
    println(treeSetForChar)
    val treeSet2=TreeSet(0,1,2,3,4,5,6,7,8,9)

    println(treeSet2)
    
    var treeMap = TreeMap("Scala" -> "Spark", "Java" -> "Hadoop")
    println(treeMap)

  

原文地址:https://www.cnblogs.com/sunrunzhi/p/9667795.html