快学scala 第三章 读书笔记及习题答案代码

本文深入讲解Scala中的数组操作,包括数组的创建、遍历、筛选、排序等实用技巧,并通过具体示例展示如何高效地处理数组数据。

chapter 3 数组相关操作

标签:快学scala


一、笔记

  1. scala的Array以java数组方式实现,数组在JVM中的类型为java.lang.String[].
  1. scala> import scala.collection.mutable.ArrayBuffer
  2. import scala.collection.mutable.ArrayBuffer
  3. scala> val b = ArrayBuffer[Int]()
  4. b: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer()
  5. scala> b+=1
  6. res0: b.type = ArrayBuffer(1)
  7. scala> b+=(1,2,3,4)
  8. res1: b.type = ArrayBuffer(1, 1, 2, 3, 4)
  9. scala> b++=Array(8,12,13)
  10. res2: b.type = ArrayBuffer(1, 1, 2, 3, 4, 8, 12, 13)

当不知道Array最终需要装多少元素,先构建一个数组缓冲,然后调用 b.toArray。 同理,a.toBuffer转换成数组缓冲。 
2. 遍历数组,until是RichInt的方法,返回所有小于但不包括上限的数字。0 until 10实际上是一个方法调用:

  1. 0.until(10)
  2. 0.until(s.length, 2) //每两个元素一跳

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

  1. scala> val a = Array(2,3,5,7,11)
  2. a: Array[Int] = Array(2, 3, 5, 7, 11)
  3. scala> val result = for(i <- a) yield i *2
  4. result: Array[Int] = Array(4, 6, 10, 14, 22)

代替守卫和yield的做法,以函数式方式添加条件操作:

  1. scala> a.filter(_ %2 == 0).map(2 * _) //取偶数,乘以2
  2. res9: Array[Int] = Array(4)
  3. scala> val a1 = a.filter(_ %2 == 0).map(2 * _)
  4. a1: Array[Int] = Array(4)

示例:移出第一个负数之外的所有负数:(传统做法是标记第一个负数)

  1. import scala.collection.mutable.ArrayBuffer
  2. object Except {
  3. def main(args: Array[String]) {
  4. val intArray = ArrayBuffer(1, -8, 10, -2, 4, -1, 3);
  5. var first = true
  6. var n = intArray.length
  7. var i = 0
  8. while(i < n){
  9. if(intArray(i) >= 0) i+=1
  10. else{
  11. if(first) { first = false; i+=1}
  12. else { intArray.remove(i); n -= 1 }
  13. }
  14. }
  15. println(intArray)
  16. }
  17. }

另外,可以将非负数拷贝到前端即可:

  1. import scala.collection.mutable.ArrayBuffer
  2. object Except {
  3. def main(args: Array[String]) {
  4. val intArray = ArrayBuffer(1, -8, 10, -2, 4, -1, 3);
  5. var flag = true
  6. val index = for(i <- 0 until intArray.length if flag || intArray(i) >= 0) yield{
  7. if(intArray(i) <0) flag = false;
  8. i
  9. }
  10. for(j <- 0 until index.length){
  11. intArray(j) = intArray(index(j))
  12. }
  13. intArray.trimEnd(intArray.length - index.length)
  14. println(intArray)
  15. }
  16. }
  1. 常用算法
  1. Array(1,7,2,3).sum
  2. ArrayBuffer("Marry","had", "a", "lamb").max
  3. scala> import scala.collection.mutable.ArrayBuffer
  4. import scala.collection.mutable.ArrayBuffer
  5. scala> val b = ArrayBuffer(1,7,2,3)
  6. b: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer(1, 7, 2, 3)
  7. val bSorted = b.sorted //b没有被改变(这里原书错误,见http://www.blogjava.net/sean/archive/2012/11/15/391386.html)
  8. scala> val bSorted = b.sortWith(_ > _) //错误见上
  9. bSorted: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer(7, 3, 2, 1)
  1. scala> scala.util.Sorting.quickSort(b)
  2. scala> b
  3. res6: Array[Int] = Array(1, 2, 3, 7)
  4. scala> b.mkString(" and ")
  5. res7: String = 1 and 2 and 3 and 7
  6. scala> b.mkString("<", ",", ">")
  7. res8: String = <1,2,3,7>
  8. scala> b.toString //java的toString在这里是毫无意义的
  9. res9: String = [I@73d9c97d

二、习题答案

3.1 编写一段代码,将a设置为一个n个随机整数的数组,要求随机数介于0(包含)和n(不包含)之间

  1. import scala.util.Random
  2. import scala.math._
  3. def randomArray(n :Int): Array[Int]= {
  4. val array = for(i<- 0 to n) yield Random.nextInt(n)
  5. array.toArray
  6. }
  7. val result = randomArray(8)
  8. for(i <- 0 until result.length) println(result(i))

3.2 编写一个循环,将整数数组中相邻的元素置换。例如,Array(1,2,3,4,5)经过置换后变为Array(2,1,4,3,5)

  1. def switch(intArray: Array[Int]): Array[Int]={
  2. val t = intArray.toBuffer
  3. for(i <- 0 until (intArray.length, 2) if i+1 < t.length) {
  4. val a = t(i)
  5. val b = t(i +1)
  6. t.remove(i, 2)
  7. t.insert(i, b)
  8. t.insert(i+1, a)
  9. }
  10. t.toArray
  11. }
  12. val a =Array(1,2,3,4,5)
  13. val b =switch(a)
  14. for(i <- 0 until b.length) println(b(i))

3.3 重复前一个练习,不过这一次生成一个新的值交换过的数组。用for/yield

  1. def switch(arr:Array[Int]):Array[Int]={
  2. val t = arr.toBuffer
  3. val result = for(i <- 0 until t.length)
  4. yield if(i%2==0 && i + 1 < t.length) t(i + 1)
  5. else if(i%2==0 && i + 1 >= t.length) t(i)
  6. else t(i - 1)
  7. result.toArray
  8. }
  9. val a =Array(1,2,3,4,5)
  10. switch(a).foreach(println(_))

3.4 给定一个整数数组,产生一个新的数组,包含元数组中的所有正值,以原有顺序排列,之后的元素是所有零或负值,以原有顺序排列

  1. import scala.collection.mutable.ArrayBuffer
  2. def reorderArray(intArray: Array[Int]): Array[Int]={
  3. val pos = ArrayBuffer[Int]()
  4. val neg = ArrayBuffer[Int]()
  5. intArray.foreach(arg => if(arg > 0) pos += arg else neg +=arg)
  6. pos ++= neg
  7. pos.toArray
  8. }
  9. val a = Array(1, -8, 10, -2, 4, -1, 3)
  10. reorderArray(a).foreach(println(_))

3.5 如何计算Array[Double]的平均值?

  1. def aveArray(arr:Array[Double]):Double={
  2. arr.sum/arr.length
  3. }

3.6 如何重新组织Array[Int]的元素将他们以反序排列?对于ArrayBuffer[Int]你又会怎么做呢?

  1. def reverseArray(arr:Array[Int]):Array[Int]={
  2. arr.reverse
  3. }

3.7 编写一段代码,产出数组中的所有值,去掉重复项。(提示:查看Scaladoc)

  1. def distinct: Array[T] //见scaladoc Array

3.8 重新编写3.4节结尾的示例。收集负值元素的下标,反序,去掉最后一个下标,然后对每个下标调用a.remove(i)。比较这样做的效率和3.4节中另外两种方法的效率

  1. import scala.collection.mutable.ArrayBuffer
  2. def removeArray(arr:Array[Int]):Array[Int]={
  3. val t = arr.toBuffer
  4. val idx = ArrayBuffer[Int]()
  5. for(i <- 0 until t.length){
  6. if(t(i) < 0) idx += i
  7. }
  8. idx.remove(0)
  9. idx.reverse
  10. idx.foreach(t.remove(_))
  11. t.toArray
  12. }
  13. val a = Array(1, -8, 10, -2, 4, -1, 3)
  14. val b = removeArray(a)
  15. for(i <- 0 until b.length)println(b(i))

3.9 创建一个由java.util.TimeZone.getAvailableIDs返回ide时区集合,判断条件是它们在美洲。去掉"America/"前缀并排序

  1. def sortAmericaTimeZone():Unit = {
  2. val array = java.util.TimeZone.getAvailableIDs
  3. val result = array.filter(_.startsWith("America")).map(_.replace("America/","")).sorted
  4. result.foreach(println(_))
  5. }
  6. sortAmericaTimeZone();

3.10 引入java.awt.datatransfer.并构建一个类型为SystemFlavorMap类型的对象: 
val flavors = SystemFlavorMap.getDefaultFlavorMap().asInstanceOf[SystemFlavorMap] 
然后以DataFlavor.imageFlavor为参数调用getNativesForFlavor方法,以Scala缓冲保存返回值。 
(为什么用这样一个晦涩难懂的类?因为在Java标准库中很难找到使用java.util.List的代码)

  1. import java.awt.datatransfer.{DataFlavor, SystemFlavorMap}
  2. import collection.JavaConversions.asScalaBuffer
  3. import scala.collection.mutable
  4. def test():Unit={
  5. val flavors = SystemFlavorMap.getDefaultFlavorMap().asInstanceOf[SystemFlavorMap]
  6. val res:mutable.Buffer[String] = flavors.getNativesForFlavor(DataFlavor.imageFlavor)
  7. println(res)
  8. }
  9. test()
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值