Scala練習(八)
控制結構和函式 |
1. 編寫示例程式,展示為什麼
package com.horstmann.impatient
不同於
package com
package horstmann
package impatient
描述: 區別是後者的上層包也可見,而串寫的只有當前包範圍可見
程式程式碼: b.scala
- package com{
- package horstmann{
- object A{
- def hi=println("I am A")
- }
- package impatient{
-
object
- def hi=A.hi
- hi
- }
- }
- }
- }
執行結果:
E:\Test>scalac b.scala
E:\Test>scala com.horstmann.impatient.B
I am A
E:\Test>
程式程式碼: c.scala
package com.horstmann.impatient{
object C extends App{
B.hi
A.hi
}
}
執行結果:
E:\Test>scalac c.scala
c.scala:4: error: not found: value A
A.hi
^
one error found
E:\Test>
編譯時找不到A,說明串聯宣告時不包含上級宣告
程式程式碼: d.scala
E:\Test>scalac d.scala
E:\Test>scala com.horstmann.impatient.C
I am A
I am A
E:\Test>
2. 編寫一段讓你的Scala朋友們感到困惑的程式碼,使用一個不在頂部的com包
程式程式碼: a1.scala
package com {
package horstmann {
package com {
package horstmann {
object A {
def hi = println("I am the Ghost A")
}
}
}
}
}
程式程式碼: a2.scala
package com {
package horstmann {
object A {
def hi =println("I am A")
}
package impatient {
object B extends App {
def hi = com.horstmann.A.hi
hi
}
}
}
}
先編譯a2.scala再編譯a1.scala執行結果如下:
E:\Test>scalac a2.scala
E:\Test>scalac a1.scala
E:\Test>scala com.horstmann.impatient.B
I am A
E:\Test>
先編譯a1.scala再編譯a1.scala執行結果如下:
E:\Test>scalac a1.scala
E:\Test>scalac a2.scala
E:\Test>scala com.horstmann.impatient.B
I am the Ghost A
E:\Test>
3. 編寫一個包random,加入函式nextlnt(): Int、nextDouble(): Double和setSeed(seed : Int): Unit。生成隨機數的演算法採用線性同餘生成器:
後值 =(前值×a+b)mod 2n
其中,a = 1664525,b =1013904223,n =32,前值的初始值為seed。
程式程式碼:
- package random{
- object Random {
- private val a = 1664525
- private val b = 1013904223
- private val n = 32
- private var seed=0
- private var follow:BigInt=0
- private var previous:BigInt=0
- def nextInt():Int={
- follow=(previous*a+b)%BigInt(math.pow(2, n).toLong)
- previous=follow
- (follow%Int.MaxValue).intValue()
- }
- def nextDouble():Double={
- nextInt.toDouble
- }
- def setSeed(newSeed:Int){
- seed=newSeed
- previous=seed
- }
- }
- }
- object Test extends App{
- var r =random.Random
- r.setSeed(args(0).toInt)
- for(i <- 1 to 10) println(r.nextInt())
- for(i <- 1 to 10) println(r.nextDouble())
- }
執行結果:
E:\Test>scalac Random.scala
E:\Test>scala Test 0
1013904223
1196435762
1372387050
720982837
1649599747
523159175
1476291629
601448361
33406696
351317787
1.27442629E9
1.020336477E9
4.8889166E8
1.654060783E9
2.8987765E7
6.3353937E7
8.92205936E8
1.338634754E9
1.649346937E9
6.21388933E8
E:\Test>
4. 在你看來,Scala的設計者為什麼要提供package object法而不是簡單地讓你將函式和變數新增到包中呢
直接加函式和變數宣告到包中,比如com.a.b.c。這樣就跟c下面的的class或者object差 了一個層級。他們實際上是c下面的所有類的共同的上級定義。這樣一來就沒有了封裝性。 而實現上來說估計也比較麻煩。
5. private[com] def giveRaise(rate: Double)的含義是什麼,有用嗎
該函式在com包下可見,可以擴大函式的可見範圍
6. 編寫一段程式,將Java雜湊對映中的所有元素拷貝到Scala雜湊對映。用引入語句重新命名這兩個類
程式程式碼:
- import java.util.{HashMap=>JHashMap}
- import scala.collection.mutable.HashMap
- object JavaMap {
- def transMapValues(javaMap:JHashMap[Any,Any]):HashMap[Any,Any]={
- val result=new HashMap[Any,Any]
- for(k <- javaMap.keySet().toArray()){
- result+=k->javaMap.get(k)
- }
- result
- }
- def main(args: Array[String]): Unit = {
- val jmap:JHashMap[Any,Any]=new JHashMap[Any,Any]
- var smap=new HashMap[Any,Any]
- for(i <- 1 to 9)
- jmap.put(i,"JavaMap"+i)
- smap=transMapValues(jmap)
- smap.foreach(println)
- }
- }
執行結果:
(8,JavaMap8)
(2,JavaMap2)
(5,JavaMap5)
(4,JavaMap4)
(7,JavaMap7)
(1,JavaMap1)
(9,JavaMap9)
(3,JavaMap3)
(6,JavaMap6)
7. 在前一個練習中,將所有引入語句移動到儘可能小的作用域裡
描述:import可以放到任何區域,直接放到物件結構體當中,也沒有問題
程式程式碼:
- object JavaMap {
- import java.util.{HashMap=>JHashMap}
- import scala.collection.mutable.HashMap
- def transMapValues(javaMap:JHashMap[Any,Any]):HashMap[Any,Any]={
- val result=new HashMap[Any,Any]
- for(k <- javaMap.keySet().toArray()){
- result+=k->javaMap.get(k)
- }
- result
- }
- def main(args: Array[String]): Unit = {
- val jmap:JHashMap[Any,Any]=new JHashMap[Any,Any]
- var smap=new HashMap[Any,Any]
- for(i <- 1 to 10)
- jmap.put(i,"JavaMap"+i)
- smap=transMapValues(jmap)
- smap.foreach(println)
- }
- }
8. 以下程式碼的作用是什麼,這是個好主意嗎
import java._
import javax._
引入了java和javax的所有內容。因為Scala會自動覆蓋java的同名類,不會有衝突。即使這樣,引入過多的包,也會讓人很迷惑。況且scala編譯就已經夠慢的了
9. 編寫一段程式,引人java.lang.System類,從user.name系統屬性讀取使用者名稱,從Console物件讀取一個密碼,如果密碼不是" secret",則在標準錯誤流中列印一個訊息;如果密碼是" secret",則在標準輸出流中列印一個問候訊息。不要使用任其他引入,也不要使用任何限定詞,即帶句點的那種
程式程式碼:
- object Sys{
- import scala.io.StdIn
- import java.lang.System._
- def main(args: Array[String]): Unit = {
- val pass=StdIn.readLine()
- if(pass=="secret"){
- val name=getProperty("user.name")
- out.printf("Greetings,%s!",name)
- }else{
- err.println("error")
- }
- }
- }
執行結果:
secret
Greetings,hadoop!
10. 除了StringBuilder,還有那些java.lang的成員是被scala包覆蓋的
Console,Math, 還有基本型別包裝物件,Long,Double,Char,Short等等都被Scala覆蓋了。
本文轉自http://www.cnblogs.com/sunddenly/p/4441485.html