chapter 3 数组相关操作
标签:快学scala
一、笔记
- scala的Array以java数组方式实现,数组在JVM中的类型为java.lang.String[].
scala> import scala.collection.mutable.ArrayBufferimport scala.collection.mutable.ArrayBufferscala> val b = ArrayBuffer[Int]()b: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer()scala> b+=1res0: b.type = ArrayBuffer(1)scala> b+=(1,2,3,4)res1: b.type = ArrayBuffer(1, 1, 2, 3, 4)scala> b++=Array(8,12,13)res2: b.type = ArrayBuffer(1, 1, 2, 3, 4, 8, 12, 13)
当不知道Array最终需要装多少元素,先构建一个数组缓冲,然后调用 b.toArray。 同理,a.toBuffer转换成数组缓冲。
2. 遍历数组,until是RichInt的方法,返回所有小于但不包括上限的数字。0 until 10实际上是一个方法调用:
0.until(10)0.until(s.length, 2) //每两个元素一跳
数组转换不会修改原数组,而是产生一个新的数组。
scala> val a = Array(2,3,5,7,11)a: Array[Int] = Array(2, 3, 5, 7, 11)scala> val result = for(i <- a) yield i *2result: Array[Int] = Array(4, 6, 10, 14, 22)
代替守卫和yield的做法,以函数式方式添加条件操作:
scala> a.filter(_ %2 == 0).map(2 * _) //取偶数,乘以2res9: Array[Int] = Array(4)scala> val a1 = a.filter(_ %2 == 0).map(2 * _)a1: Array[Int] = Array(4)
示例:移出第一个负数之外的所有负数:(传统做法是标记第一个负数)
import scala.collection.mutable.ArrayBufferobject Except {def main(args: Array[String]) {val intArray = ArrayBuffer(1, -8, 10, -2, 4, -1, 3);var first = truevar n = intArray.lengthvar i = 0while(i < n){if(intArray(i) >= 0) i+=1else{if(first) { first = false; i+=1}else { intArray.remove(i); n -= 1 }}}println(intArray)}}
另外,可以将非负数拷贝到前端即可:
import scala.collection.mutable.ArrayBufferobject Except {def main(args: Array[String]) {val intArray = ArrayBuffer(1, -8, 10, -2, 4, -1, 3);var flag = trueval index = for(i <- 0 until intArray.length if flag || intArray(i) >= 0) yield{if(intArray(i) <0) flag = false;i}for(j <- 0 until index.length){intArray(j) = intArray(index(j))}intArray.trimEnd(intArray.length - index.length)println(intArray)}}
- 常用算法
Array(1,7,2,3).sumArrayBuffer("Marry","had", "a", "lamb").maxscala> import scala.collection.mutable.ArrayBufferimport scala.collection.mutable.ArrayBufferscala> val b = ArrayBuffer(1,7,2,3)b: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer(1, 7, 2, 3)val bSorted = b.sorted //b没有被改变(这里原书错误,见http://www.blogjava.net/sean/archive/2012/11/15/391386.html)scala> val bSorted = b.sortWith(_ > _) //错误见上bSorted: scala.collection.mutable.ArrayBuffer[Int] = ArrayBuffer(7, 3, 2, 1)
scala> scala.util.Sorting.quickSort(b)scala> bres6: Array[Int] = Array(1, 2, 3, 7)scala> b.mkString(" and ")res7: String = 1 and 2 and 3 and 7scala> b.mkString("<", ",", ">")res8: String = <1,2,3,7>scala> b.toString //java的toString在这里是毫无意义的res9: String = [I@73d9c97d
二、习题答案
3.1 编写一段代码,将a设置为一个n个随机整数的数组,要求随机数介于0(包含)和n(不包含)之间
import scala.util.Randomimport scala.math._def randomArray(n :Int): Array[Int]= {val array = for(i<- 0 to n) yield Random.nextInt(n)array.toArray}val result = randomArray(8)for(i <- 0 until result.length) println(result(i))
3.2 编写一个循环,将整数数组中相邻的元素置换。例如,Array(1,2,3,4,5)经过置换后变为Array(2,1,4,3,5)
def switch(intArray: Array[Int]): Array[Int]={val t = intArray.toBufferfor(i <- 0 until (intArray.length, 2) if i+1 < t.length) {val a = t(i)val b = t(i +1)t.remove(i, 2)t.insert(i, b)t.insert(i+1, a)}t.toArray}val a =Array(1,2,3,4,5)val b =switch(a)for(i <- 0 until b.length) println(b(i))
3.3 重复前一个练习,不过这一次生成一个新的值交换过的数组。用for/yield
def switch(arr:Array[Int]):Array[Int]={val t = arr.toBufferval result = for(i <- 0 until t.length)yield if(i%2==0 && i + 1 < t.length) t(i + 1)else if(i%2==0 && i + 1 >= t.length) t(i)else t(i - 1)result.toArray}val a =Array(1,2,3,4,5)switch(a).foreach(println(_))
3.4 给定一个整数数组,产生一个新的数组,包含元数组中的所有正值,以原有顺序排列,之后的元素是所有零或负值,以原有顺序排列
import scala.collection.mutable.ArrayBufferdef reorderArray(intArray: Array[Int]): Array[Int]={val pos = ArrayBuffer[Int]()val neg = ArrayBuffer[Int]()intArray.foreach(arg => if(arg > 0) pos += arg else neg +=arg)pos ++= negpos.toArray}val a = Array(1, -8, 10, -2, 4, -1, 3)reorderArray(a).foreach(println(_))
3.5 如何计算Array[Double]的平均值?
def aveArray(arr:Array[Double]):Double={arr.sum/arr.length}
3.6 如何重新组织Array[Int]的元素将他们以反序排列?对于ArrayBuffer[Int]你又会怎么做呢?
def reverseArray(arr:Array[Int]):Array[Int]={arr.reverse}
3.7 编写一段代码,产出数组中的所有值,去掉重复项。(提示:查看Scaladoc)
def distinct: Array[T] //见scaladoc Array
3.8 重新编写3.4节结尾的示例。收集负值元素的下标,反序,去掉最后一个下标,然后对每个下标调用a.remove(i)。比较这样做的效率和3.4节中另外两种方法的效率
import scala.collection.mutable.ArrayBufferdef removeArray(arr:Array[Int]):Array[Int]={val t = arr.toBufferval idx = ArrayBuffer[Int]()for(i <- 0 until t.length){if(t(i) < 0) idx += i}idx.remove(0)idx.reverseidx.foreach(t.remove(_))t.toArray}val a = Array(1, -8, 10, -2, 4, -1, 3)val b = removeArray(a)for(i <- 0 until b.length)println(b(i))
3.9 创建一个由java.util.TimeZone.getAvailableIDs返回ide时区集合,判断条件是它们在美洲。去掉"America/"前缀并排序
def sortAmericaTimeZone():Unit = {val array = java.util.TimeZone.getAvailableIDsval result = array.filter(_.startsWith("America")).map(_.replace("America/","")).sortedresult.foreach(println(_))}sortAmericaTimeZone();
3.10 引入java.awt.datatransfer.并构建一个类型为SystemFlavorMap类型的对象:
val flavors = SystemFlavorMap.getDefaultFlavorMap().asInstanceOf[SystemFlavorMap]
然后以DataFlavor.imageFlavor为参数调用getNativesForFlavor方法,以Scala缓冲保存返回值。
(为什么用这样一个晦涩难懂的类?因为在Java标准库中很难找到使用java.util.List的代码)
import java.awt.datatransfer.{DataFlavor, SystemFlavorMap}import collection.JavaConversions.asScalaBufferimport scala.collection.mutabledef test():Unit={val flavors = SystemFlavorMap.getDefaultFlavorMap().asInstanceOf[SystemFlavorMap]val res:mutable.Buffer[String] = flavors.getNativesForFlavor(DataFlavor.imageFlavor)println(res)}test()
本文深入讲解Scala中的数组操作,包括数组的创建、遍历、筛选、排序等实用技巧,并通过具体示例展示如何高效地处理数组数据。
264

被折叠的 条评论
为什么被折叠?



