美文网首页
scala04.数据结构(重点)

scala04.数据结构(重点)

作者: Java架构师之路 | 来源:发表于2018-11-22 15:12 被阅读0次

    第4章数据结构(重点练习章节)

    4.1主要的集合特质

    4.1主要的集合特质
    Scala同时支持可变集合和不可变集合,
    不可变集合从不可变,可以安全的并发访问。

    4.2数组

    Scala优先采用不可变集合。
    集合主要分为三大类:序列、集、映射
    所有集合都扩展自Iterable特质。
    对于几乎所有的集合类,Scqla都同时提供了可变和不可变的版本。
    Seq是一个有先后次序的值得序列。
    IndexedSeq能够通过整形下标快速访问元素。
    Set是一个没有先后次序的值集合。
    在SortedSort中,元素以某种排过序的顺序被访问。
    Map是一组键值对偶,SortedMap按照键的排序访问其中的实体。

    4.2.1定长数组

    如果需要一个定长数组,可以使用Scala中的Array,Array 以java数组的方式实现。

    4.2.2变长数组

    变长数组可以使用ArrayBuffer,Java中有ArrayList

    4.2.3数组转换

    转换动作不会修改原数组,而是产生一个新的数组。

    4.2.4多维数组

    和Java一样,多维数组通过数组的数组来实现,可以用ofDim方法。

    4.2.5和Java数组的互操作

    Scala数组是通过Java进行实现的
    使用scala.collection.convert.AsJavaConverters
    或者AsScalaConverters进行转换

    4.3映射

    4.3.1映射操作

    映射就是key-value的集合,就类似于Java中的Map。

    不可变映射也可以调用方法,只不过产生新的映射。
    新映射和老映射共享大部分结构。可变映射是在原映射基础上进行修改。

    4.3.2和Java的互操作

    使用JavaConversions进行转换

    4.4元组

    元组是不同类型的值的聚集
    元组使用_1,_2,_3来访问

    元组是从1开始不是0;
    元组可用于函数需要返回不止一个值得情况

    4.5队列

    队列是一个先进先出的结构:

    4.6堆栈

    Stack是一个先进后出的结构

    4.7列表

    如果List为空,用Nil来表示。

    4.8集

    集是不重复元素的结合。集不保留顺序,默认是以哈希集实现。

    4.9添加去除元素操作符

    1.向后(:+)或向前(+:)追加元素到序列当中。
    2.添加(+)元素到无先后次序的集合中。
    3.用-移除元素。
    4.用++和--来批量添加和移除元素。
    5.对于列表,优先使用::和.
    6.改值操作有+=、++=、-=和--=。
    7.对于集合,我更喜欢++、--和--=。
    8.我尽量不用++:、+:和++-:。

    4.10常用方法

    4.11将函数映射到集合

    map应用于集合中的每一个元素,并产生转换后的一个新元素。
    flatmap同样应用于集合的每一个元素,对于每一个元素产出一个集合,并将集合中的元素串接在一起。

    4.12化简、折叠、扫描

    将二元函数应用于集合中的元素

    4.13拉链操作

    作用于两个集合,将对应的元素合并成一个元组。

    4.14迭代器

    通过iterator方法从集合获得一个迭代器

    4.15流(不可变列表)

    流Stream只有在需要的时候才会去计算下一个元素

    4.16懒视图

    :: 返回一个流
    view不会缓存数据,每次都要重新计算

    4.17与java集合的互操作总结。

    4.18线程安全的集合

    Scala类库提供了6个并发特质,可以通过混入这些集合,让集合的操作变成同步的

    4.19并行集合

    Scala为了充分使用多核CPU,提供了并行集合(有别于前面的串行集合),用于多核环境的并行计算。

    并行集合位于scala.collection.parallel,分immutable和mutable。
    通过par关键字将集合转换为一个并行集合
    通过ser方法将并行集合转换回串行集合。
    注意:在并行任务里面,不要同时更新一个共享变量。

    4.20操作符概述

    1、如果想在变量名、类名等定义中用保留字,可以用反引号:val‘val'=42
    2、这种形式叫中置操作符,A操作符B等同于A.操作符(B)
    3、后置操作符,A操作符等同于,A.操作符,如果操作符定义的时候不带()则调用时不能加()
    4、前置操作符,+、一、!、~等操作符A等同于A.unary_操作符
    5、赋值操作符,A操作符=B等同于A=A操作符B

    import java.awt.Font
    
    import org.scalatest.FunSuite
    
    class Chapter03CoreTest extends FunSuite {
    
      test("core01") {
        //定长数组
        val s = Array("Hello", "World")
        println(s.mkString(","))
        s(1) = "scala"
        //变长数组
        import scala.collection.mutable.ArrayBuffer
        var arrayBuffer = new ArrayBuffer[Int]()
        //元素追加
        arrayBuffer += 1
        arrayBuffer += (2, 3, 4, 5)
        arrayBuffer ++= Array(8, 13, 21)
        println(arrayBuffer.mkString(","))
        //元素移除
        arrayBuffer.trimEnd(2)
        //元素插入
        arrayBuffer.insert(2, 6)
        println(arrayBuffer.mkString(","))
    
        //变长数组语定长数组之间的互转
        val array1 = arrayBuffer.toArray
        val buffer1 = s.toBuffer
        //数组的遍历
        for (i <- 0 to arrayBuffer.size - 1) println(arrayBuffer(i))
        // 数组通过下标访问
        for (i <- 0 until array1.length)
          println(i + ": " + array1(i))
        //产生一个Range序列
        val range1 = 0 until(4, 1)
        println(range1.reverse)
        // a 遍历
        for (elem <- array1)
          println(elem)
    
        // a 索引
        for (i <- array1.indices)
          println(i + ": " + array1(i))
    
      }
    
      test("core02") {
        // 产生新的数组
        val a = Array(2, 3, 4, 5)
        val result = for (i <- a) yield 2 * i
        //数组转字符串
        println(result.mkString(","))
        //数组排序
        result.sorted
        //快速排序
        scala.util.Sorting.quickSort(result)
        println(result.mkString(","))
        println(result.toString)
        //统计大于0的个数
        println(result.count(_ > 0))
        import scala.collection.mutable.ArrayBuffer
        var buffer = ArrayBuffer(1, 2, 3)
        //追加
        buffer.append(1)
        //追加数组
        buffer.appendAll(ArrayBuffer(1, 2, 3))
        val result2 = Array(1)
        //    result2.copyToArray(result)
        //添加20项 使用-1填充
        result2.padTo(20, -1)
      }
      test("core03") {
        //多维数组 矩阵 3行四列
        val matrix = Array.ofDim[Double](3, 4)
        val row = 0
        val column = 2
        //赋值
        matrix(0)(2) = 18.99
        println(matrix.length)
        println(matrix(row).length)
    
      }
      test("core04") {
        // scala 和Java的相互操作
        import scala.collection.JavaConversions._
        import scala.collection.mutable
        import scala.collection.mutable.ArrayBuffer
    
        val command = ArrayBuffer("ls", "-al", "/")
        //    val pb = new ProcessBuilder(command.asJava)
        //    val cmd:mutable.Buffer[String] = pd.command().asScala
        //    assert(cmd == command)
      }
      test("core05") {
        //不可变的map "Jim" -> 10称为对偶
        val map1 = Map("Jim" -> 10, "Bob" -> 3, "lucy" -> 8)
        //可变的map
        val map2 = scala.collection.mutable.Map("Jim" -> 10, "Bob" -> 3, "lucy" -> 8)
        // 空映射
        val scores = new scala.collection.mutable.HashMap[String, Int]
        //对偶元组
        val map3 = Map(("Alice1", 11), ("Alice2", 11), ("Alice3", 11))
        //取值
        println(map1.get("Jim"))
        println(map1.getOrElse("Jim", "0"))
        // contains检测
        val fredsScore = if (scores.contains("Fred")) scores("Fred") else 0
        //设置参数值
        map1("Jim") = 100
        //    map1("Bob")=11
        //遍历map
        for ((k, v) <- map1) println(k + "is mapped to" + v)
        //keyset集合
        val set = map1.keySet
        //遍历所有的value
        for (v <- map1.values) println(v)
        //产生新的Map
        for ((k, v) <- map1) yield (v, k)
        //排序的map
        val map4 = scala.collection.immutable.SortedMap("Alice" -> 10, "Fred" -> 11)
        //双向链表HashMap
        val months = scala.collection.mutable.LinkedHashMap("Jan" -> 1)
    
    
      }
      test("core06") {
        //map和Java的相互转换
        import scala.collection.JavaConverters._
        val ids = java.time.ZoneId.SHORT_IDS.asScala
    
        val props = System.getProperties.asScala
        import java.awt.font.TextAttribute._
        val attrs = Map(FAMILY -> "Serif", SIZE -> 12)
        val front = new Font(attrs.asJava)
      }
      test("core07") {
        //元祖
        val tuple = (1, 2, 3, "Fred")
        //元祖访问
        val second = tuple._2
        //元祖访问
        val first = tuple._1
    
        //拉链操作
        val symbols = Array("<", "-", ">")
        val counts = Array(2, 10, 2)
        //zip 拉链操作
        val pairs = symbols.zip(counts)
        //遍历
        for ((s, n) <- pairs) println(s * n)
        //拉链操作 转Map
        symbols.zip(counts).toMap
      }
      test("core08") {
        import scala.collection.mutable
        //声明一个队列
        val q1 = new mutable.Queue[Int]()
        //队列追加元素
        q1 += 2
        q1 += 1
        //追加多个元素并返回队列
        q1 ++= List(2, 3)
        //返回并从队列删除第一个元素
        q1.dequeue()
        //追加多个元素 返回Unit
        q1.enqueue(5, 3, 6)
        //头
        print(q1.head)
        //尾
        print(q1.tail)
    
      }
      test("core09") {
    
        import scala.collection.mutable
        //声明一个栈
        val s = new mutable.Stack[Int]()
        //入栈
        s.push(1)
        s.push(1, 2)
        //出栈
        s.pop()
        s.push(3)
        //获取栈顶元素
        s.top
      }
      test("core10") {
        //列表
        val digists = List(4, 2)
        //右边结合操作符
        9 :: List(4, 2)
    
        //NIL表示空列表
        9 :: 4 :: 2 :: Nil
    
        //    9 :: (4 :: (2 :: Nil))
        sum(List(1, 2, 3))
        sum2(List(1, 2, 3))
        //sum求和
        List(1, 2, 3).sum
      }
    
      def sum(lst: List[Int]): Int = if (lst == Nil) 0 else lst.head + sum(lst.tail)
    
      def sum2(lst: List[Int]): Int = lst match {
        case Nil => 0
        case h :: t => h + sum(t)
      }
    
      test("core11") {
        //set不可重复集合
        var numberSet = Set(1, 2, 3)
        //set 追加元素
        numberSet += 5
        //set 大小
        println(numberSet.size)
        //set 减去元素
        Set(1, 2, 3) - 3
        //set 追加元素
        Set(1, 2, 3) + 1
        //遍历 set
        for (x <- Set(1, 2, 3)) println(x)
    
      }
      test("core12") {
        //map映射
        val names = List("Peter", "Paul", "Mary")
        //map
        names.map(_.toLowerCase) // List("PETER", "PAUL", "MARY")
        //等价于map操作
        for (n <- names) yield n.toUpperCase()
        //flatMap操作 打平
      }
    
      //  def ulcase(s: String) = Vector(s.toLowerCase(), s.toUpperCase)
    
      test("core13") {
        //部分简化操作
        List(1, 2, 3).reduceLeft(_ - _)
        List(1, 2, 3).reduceRight(_ - _)
        //折叠操作
        List(1, 2, 3, 4).foldLeft(0)(_ - _)
    
        val freq = scala.collection.mutable.Map[Char, Int]()
    
        for (c <- "Miss") freq(c) = freq.getOrElse(c, 0) + 1
    
        //扫描操作
        (1 to 10).scanLeft(0)(_ + _)
    
    
      }
      test("core14") {
        val prices = List(1, 2, 3)
        val quantites = List(1, 2, 3)
        prices zip quantites
        //拉链后执行map操作
        (prices zip quantites) map { p => p._1 * p._2 }
        List(1, 2, 3) zip List(1, 2, 3)
        List(1, 2, 3).zipAll(List(10, 2), 0, 2)
        "Scala".zipWithIndex
        "Scala".zipWithIndex.max
        "Scala".zipWithIndex.max._2
        //unzip函数可以将一个元素的列表转换成一个列表的元祖
        "scala".zipWithIndex.unzip
        "scala".zipWithIndex.unzip._1
        "scala".zipWithIndex.unzip._2
      }
      test("core15") {
        //切片操作返回一个迭代器
        val iterator = (1 to 10).sliding(3)
        while (iterator.hasNext) println(iterator.next())
        val iterable2 = (1 to 10).sliding(3)
        //遍历长度
        for (i <- iterable2) print(i)
        //获取长度
        println(iterable2.length)
        //iterable2 会移动指针
        println(iterable2.hasNext)
        //返回迭代器数组
        println(iterable2.toArray)
      }
    
      // #::返回一个流
      def numsForm(n: BigInt): Stream[BigInt] = n #:: numsForm(n + 1)
    
      test("core16") {
        val tenOrMore = numsForm(10)
        //尾部
        tenOrMore.tail
        //头部
        tenOrMore.head
        //最后一个元素
        tenOrMore.tail.tail.tail
        //对流执行求值运算
        val squares = numsForm(5).map(x => x * x)
        squares.take(5).force
      }
    
      def sq(x: Int): Stream[Int] = {
        println(x)
        x * x
      } #:: sq(x + 1)
    
      test("core17") {
        //view的懒执行 不是很好理解
        //view不会缓存数据,每次都要重新计算
        //    import scala.math._
        val p = (1 to 10).view.map(x => {
          println(x)
          x * x
        })
        p.take(10).mkString(",")
        val p1 = sq(0)
        p1(10)
        p1.take(10).last
      }
      test("core18") {
        //通过par关键字将集合转换为一个并行集合
        (1 to 5).par.foreach { 
          it => println(Thread.currentThread().getName()); print("^" + it)
      }
        val c = (1 to 5).map(_ + 100)
        println(c)
      }
    }
    
    

    相关文章

      网友评论

          本文标题:scala04.数据结构(重点)

          本文链接:https://www.haomeiwen.com/subject/fzulqqtx.html