自拍偷在线精品自拍偷,亚洲欧美中文日韩v在线观看不卡

Scala,一門「特立獨(dú)行」的語(yǔ)言!

開(kāi)發(fā) 后端
入門 Spark 的路上很難不接觸 Scala 。Scala 似乎是為 java 提供了很多『類似函數(shù)式編程』的語(yǔ)法糖,這里記錄一下這個(gè)語(yǔ)言獨(dú)特的地方分享給讀者朋友們。

[[410308]]

本文轉(zhuǎn)載自微信公眾號(hào)「Piper蛋窩」,作者Piper蛋 。轉(zhuǎn)載本文請(qǐng)聯(lián)系Piper蛋窩公眾號(hào)。

入門 Spark 的路上很難不接觸 Scala 。Scala 似乎是為 java 提供了很多『類似函數(shù)式編程』的語(yǔ)法糖,這里記錄一下這個(gè)語(yǔ)言獨(dú)特的地方分享給讀者朋友們。

參考資料主要有:

  • 曹潔 . Spark大數(shù)據(jù)分析技術(shù)(Scala版)[M]. 北京航空航天大學(xué)出版社, 2021. ISBN:9787512433854
  • 陳歡 , 林世飛 . Spark最佳實(shí)踐[M]. 人民郵電出版社, 2016. ISBN:9787115422286

Scala 基本思想與注意事項(xiàng)

Sacla 即 Scalable Language ,正如其名,是一門可伸縮的編程語(yǔ)言:

  • 基于 java 的虛擬機(jī)( Scala 會(huì)被編譯成 JVM 字節(jié)碼)
  • 但是既可以當(dāng)腳本使用,又可以構(gòu)造大型系統(tǒng)
  • 是靜態(tài)語(yǔ)言,但是可以像動(dòng)態(tài)語(yǔ)言那樣支持交互式編程
  • 面型對(duì)象:每一個(gè)值都是對(duì)象,每一次運(yùn)算都是一次方法調(diào)用
  • 函數(shù)式編程:所有函數(shù)都是對(duì)象,函數(shù)是“一等公民”
  • Scala 中幾乎一切都是表達(dá)式

scala 是解釋器, scalac 是編譯器;可以直接 scala test.scala ,也可以 scalac test.scala & scala test (先把源碼編譯為字節(jié)碼,再把字節(jié)碼放到虛擬機(jī)中解釋運(yùn)行)。還可用輸入 scala 進(jìn)入交換編程界面。

所以要注意的是,需要先安裝 JDK ,并且設(shè)置好環(huán)境變量 JAVA_HOME 。此外,更加重要的是, Scala 小版本兼容:2.12.x 與 2.13.x 這兩者不兼容,2.12.10 與 2.12.11 才兼容。

最基本的語(yǔ)法示例

類型的聲明、控制結(jié)構(gòu)(for、模式匹配、case)

  1. // 變量 
  2. val two: Int = 1 + 1 
  3.  
  4. var one: Int = 1 
  5. var one: String = 'one' 
  6.  
  7. // 函數(shù) 
  8. def addOne(x: Int): Int = x + 1 
  9.  
  10. def add(x: Int, y: Int): Int = { 
  11.     x + y 
  12.  
  13. // 部分控制結(jié)構(gòu) 
  14. var filename =  
  15.     if (!args.isEmpty) args(0) 
  16.     else "default.txt" 
  17.  
  18. for (i <- 1 to 4) 
  19.     println("iteration " + i) 

1 to 4 是 [1,2,3,4] ,而 i until 4 是 [1,2,3] 。

關(guān)于 for 還有一些奇技淫巧。

  1. // 多個(gè)區(qū)間 
  2. for (a <- 1 to 2; b <- 1 to 2) { 
  3.     println("a: " + a + ", b: " + b) 
  4. // 結(jié)果 
  5. a: 1, b: 1 
  6. a: 1, b: 2 
  7. a: 2, b: 1 
  8. a: 2, b: 2 
  9.  
  10. // 過(guò)濾器 
  11. val list1 = List(3, 5, 2, 1, 7) 
  12. for (x <- list1 if x % 2 == 1) print(" " + x) 
  13. // 3 5 1 7 

關(guān)于模式匹配,則有更多奇技淫巧。這里我直接參考:scala中case的用法[1]

  1. // 一.簡(jiǎn)單匹配,值匹配: 
  2.  
  3. val bools = List(truefalse
  4. for (bool <- bools) { 
  5.     bool match { 
  6.         case true => println("heads"
  7.         case false => println("tails"
  8.         case _ => println("something other than heads or tails (yikes!)"
  9.     } 
  10.  
  11. import scala.util.Random 
  12. val randomInt = new Random().nextInt(10) 
  13. randomInt match { 
  14.     case 7 => println("lucky seven!"
  15.     case otherNumber => println("boo, got boring ol' " + otherNumber) 
  16.  
  17. // 二. 類型匹配 
  18.  
  19. val sundries = List(23, "Hello", 8.5, 'q'
  20. for (sundry <- sundries) { 
  21.     sundry match { 
  22.         case i: Int => println("got an Integer: " + i) 
  23.         case s: String => println("got a String: " + s) 
  24.         case f: Double => println("got a Double: " + f) 
  25.         case other => println("got something else: " + other) 
  26.  
  27. // 三 根據(jù)順序匹配 
  28.  
  29. val willWork = List(1, 3, 23, 90) 
  30. val willNotWork = List(4, 18, 52) 
  31. val empty = List() 
  32. for (l <- List(willWork, willNotWork, empty)) { 
  33.     l match { 
  34.         case List(_, 3, _, _) => println("Four elements, with the 2nd being '3'."
  35.         case List(_*) => println("Any other list with 0 or more elements."
  36.     } 
  37.  
  38. // 四 case里面用 guard 的數(shù)組匹配 
  39.  
  40. val tupA = ("Good""Morning!"
  41. val tupB = ("Guten""Tag!"
  42.     for (tup <- List(tupA, tupB)) { 
  43.         tup match { 
  44.             case (thingOne, thingTwo) if thingOne == "Good" => 
  45.             println("A two-tuple starting with 'Good'."
  46.             case (thingOne, thingTwo) =>println("This has two things: " + thingOne + " and " + thingTwo) 
  47.         } 
  48.  
  49. // 五 對(duì)象深度匹配 
  50.  
  51. case class Person(name: String, age: Int
  52. val alice = new Person("Alice", 25) 
  53. val bob = new Person("Bob", 32) 
  54. val charlie = new Person("Charlie", 32) 
  55. for (person <- List(alice, bob, charlie)) { 
  56.     person match { 
  57.         case Person("Alice", 25) => println("Hi Alice!"
  58.         case Person("Bob", 32) => println("Hi Bob!"
  59.         case Person(name, age) => 
  60.             println("Who are you, " + age + " year-old person named " + name + "?"
  61.     } 
  62.  
  63. // 六 正則表達(dá)式匹配 
  64.  
  65. val BookExtractorRE = """Book: title=([^,]+),\s+authors=(.+)""".r 
  66. val MagazineExtractorRE = """Magazine: title=([^,]+),\s+issue=(.+)""".r 
  67.  
  68. val catalog = List( 
  69.     "Book: title=Programming Scala, authors=Dean Wampler, Alex Payne"
  70.     "Magazine: title=The New Yorker, issue=January 2009"
  71.     "Book: title=War and Peace, authors=Leo Tolstoy"
  72.     "Magazine: title=The Atlantic, issue=February 2009"
  73.     "BadData: text=Who put this here??" 
  74.  
  75. for (item <- catalog) { 
  76.     item match { 
  77.         case BookExtractorRE(title, authors) => 
  78.             println("Book \"" + title + "\", written by " + authors) 
  79.         case MagazineExtractorRE(title, issue) => 
  80.             println("Magazine \"" + title + "\", issue " + issue) 
  81.         case entry => println("Unrecognized entry: " + entry) 
  82.     } 

關(guān)于 case ,我想強(qiáng)調(diào)其在“解包”中的應(yīng)用:

  1. dict = Map("Piper" -> 95, "Bob" -> 90) 
  2. dict.foreach { 
  3.     case (k, v) => printf( 
  4.         "grade of %s is %s/n", k, v 
  5.     ) 
  6.  
  7. grade of Piper is 95 
  8. grade of Bob is 90 

上述:使用了 foreach { case () => {} } ,注意 foreach 的大括號(hào)。與下面等效。

  1. dict = Map("Piper" -> 95, "Bob" -> 90) 
  2. dict.foreach ( 
  3.     x => println( 
  4.         s"grade of ${x._1} is ${x._2}" 
  5.     ) 
  6.  
  7. grade of Piper is 95 
  8. grade of Bob is 90 

Scala 語(yǔ)法獨(dú)特的地方

無(wú)參數(shù)方法,調(diào)用時(shí)不用加括號(hào):args.isEmpty。

  1. def width: Int = if (height == 0) 0 else contents(0).length 
  2.  
  3. width  // 調(diào)用 

for 中使用 <- ,相當(dāng)于 Python 的 in 。

繼承用關(guān)鍵字 extends :class A(a: Int) extends B 。

單實(shí)例對(duì)象 / 靜態(tài)成員變量與方法定義在 object 中:

  1. object Timer { 
  2.     var count = 0 
  3.     def currentCount() : Long = { 
  4.         count += 1 
  5.         count 
  6.     } 
  7.  
  8. Timer.currentCount()  // 直接調(diào)用 
  9.  
  10. class Timer { 
  11.     ... 

函數(shù)返回不必非要加 return ,默認(rèn)最后一個(gè)表達(dá)式。

函數(shù)式:匿名函數(shù)作為參數(shù),并且還可以更簡(jiǎn)潔

  1. val numbers = List(1, -3, -5, 9, 0) 
  2.  
  3. numbers.filter((x) => x > 0) 
  4. numbers.filter(x => x > 0) 
  5. numbers.filter(_ > 0)  // 一個(gè)參數(shù)且函數(shù)中僅被使用一次時(shí) 

_ 具有特殊的意義與工作(占位)

  1. // 部分應(yīng)用函數(shù) 
  2. def adder(m: Int, n: Int) = m + n 
  3.  
  4. val add2 = adder(2, _: Int)  // add2: (Int) => Int = <function1> 
  5. add2(3)  // res1: Int = 5 
  6.  
  7. // 柯里化 currying 
  8. def curriedSum(x: Int)(y: Int) = x + y 
  9. curriedSum (1)(2) 
  10.  
  11. val onePlus = curriedSum(1)_  // 注意這里使用了 _ 
  12. onePlus(2) 
  13.  
  14. // 模式匹配 
  15. var times = 1 
  16. times match { 
  17.     case 1 => "one" 
  18.     case 2 => "two" 
  19.     case _ => "other" 

Scala 的面向?qū)ο笈c一等公民“函數(shù)”

  1. (1).+(2)  // 3 

如上,(1)是對(duì)象,.+(2)是方法調(diào)用。Scala 中萬(wàn)物皆對(duì)象。

  1. var increase = (x: Int) => x + 1 

如上,函數(shù)是一等公民,可以賦值給變量。

基本數(shù)據(jù)結(jié)構(gòu)

有以下概念:

  • 不可變列表 List 與可變列表 ListBuffer
  • 定長(zhǎng)數(shù)組 Array 與變長(zhǎng)數(shù)組 ArrayBuffer
  • 不可變集合 Set 與可變集合 scala.collection.mutable.Set
  • 映射 Map 與 可變映射 scala.collection.mutable.Map
  • 元組 Tuple

注意事項(xiàng)與 Scala 奇技淫巧

使用 until 是遍歷數(shù)組的好辦法,by 和 _* 特殊意義:

  1. for (i <- 0 until.length) { } 
  2.  
  3. Array (1,3,5,7,9,11)  // 等價(jià)于 
  4. Array[Int](1 to 11 by 2:_* "Int")  // _* 有種解包的意味 

使用 yield 生成數(shù)組

  1. val a = Array(1, 2, 3, 4) 
  2. val res1 = for (ele <- a) yield 2 * ele 
  3. // 2, 4, 6, 8 

元組的下標(biāo)從 1 開(kāi)始

  1. val person = (1, 2, "ABC"
  2. person._1  // 1 

拉鏈操作 zip

  1. val symbols = Array("<""-"">"
  2. val counts = Array(2, 10, 2) 
  3. val pairs = symbols.zip(counts) 
  4. // Array[(String, Int)] = Array((<, 2), (-, 10), (>, 2)) 
  5. for ((s, n) <- pairs) print(s * n) 
  6. <<---------->> 

Map 神奇操作

  1. // 創(chuàng)建 
  2. val dict = Map("Piper" -> 95, "Bob" -> 90) 
  3. val kv   = Map(("Piper", 95), ("Bob", 90)) 
  4.  
  5. // 取值 
  6. dict("Piper"
  7.  
  8. // 合并 ++ 
  9. dict ++ kv 
  10. dict.++(kv) 
  11.  
  12. // 添加 + ,刪除 - 
  13. val n = dict + ("Tom" -> 91) 
  14. val l = dict - "Tom" 

對(duì)于可變 Map :

  1. // += -= 
  2. dict += (("Tom", 91), ("Jerry", 87)) 
  3. dict -= "Tom" 
  4. dict -= ("Jerry""Bob"
  5.  
  6. // ++= --= 與其他集合相聯(lián)系 
  7. dict ++= List(("Tom", 91), ("Jerry", 87)) 
  8. dict --= List("Jerry", "Bob") 

:: 與 ::: 創(chuàng)建列表

  1. 1::3::5::Nil  // List[Int] = List(1, 3, 5) 

注意 :: 是右結(jié)合的:(1::(3::(5::Nil))) 。

  1. // ::: 用來(lái)連接列表 
  2. val L4 = L3 ::: List("Hadoop""Hbase"

關(guān)于數(shù)據(jù)結(jié)構(gòu)的討論(List or Array?)

  • 多用 List 而非 Array
  • 列表的結(jié)構(gòu)是遞歸的(即鏈表,linkedList),而數(shù)組是平等的

參考:

  • scala中List、Array、ListBuffer、ArrayList、Set、元組區(qū)別[2]
  • Scala學(xué)習(xí)筆記5 (集合 Collections)[3]

參考資料

[1]scala中case的用法: https://blog.csdn.net/qq_41669665/article/details/86158993

[2]scala中List、Array、ListBuffer、ArrayList、Set、元組區(qū)別: https://blog.csdn.net/mar_ljh/article/details/81910286

[3]Scala學(xué)習(xí)筆記5 (集合 Collections): https://blog.csdn.net/lyrebing/article/details/20362227

【責(zé)任編輯:武曉燕 TEL:(010)68476606】

 

責(zé)任編輯:武曉燕 來(lái)源: Piper蛋窩
相關(guān)推薦

2011-05-01 21:48:54

Ubuntu 11.0

2019-11-18 11:00:58

程序員編程語(yǔ)言

2015-07-28 15:35:48

學(xué)習(xí)語(yǔ)言

2012-03-28 09:40:40

JavaScript

2011-12-30 09:33:02

程序員語(yǔ)言

2014-12-03 09:48:36

編程語(yǔ)言

2012-09-04 11:20:31

2022-02-27 14:45:16

編程語(yǔ)言JavaC#

2022-11-04 11:11:15

語(yǔ)言入職項(xiàng)目

2017-04-07 16:49:00

語(yǔ)言程序編程

2017-04-07 10:45:43

編程語(yǔ)言

2024-06-27 09:00:00

人工智能編程語(yǔ)言軟件開(kāi)發(fā)

2020-09-27 15:52:02

編程語(yǔ)言C 語(yǔ)言Python

2023-02-08 07:35:43

Java語(yǔ)言面向?qū)ο?/a>

2022-02-21 11:15:59

編程語(yǔ)言后端開(kāi)發(fā)

2022-09-07 08:05:32

GScript?編程語(yǔ)言

2011-07-14 17:58:11

編程語(yǔ)言

2017-10-26 11:44:19

工具語(yǔ)言編寫

2018-07-16 12:36:48

編程語(yǔ)言PythonJava

2015-08-17 15:12:56

新技術(shù)語(yǔ)言框架
點(diǎn)贊
收藏

51CTO技術(shù)棧公眾號(hào)