現在您已了解如何撰寫自己的高階函式,讓我們快速瀏覽更實際的範例。
想像一下 List
類別沒有自己的 map
方法,而您想要撰寫自己的方法。在建立函式時,第一步是準確說明問題。僅專注於 List[Int]
,您會說明
我想撰寫一個
map
方法,可以用於將函式套用至List[Int]
中的每個元素,並將轉換後的元素傳回為新的清單。
根據該說明,您開始撰寫方法簽章。首先,您知道您想接受函式作為參數,而該函式應將 Int
轉換為某個泛型類型 A
,因此您撰寫
def map(f: (Int) => A)
使用泛型類型的語法需要在參數清單前宣告該類型符號,因此您加入
def map[A](f: (Int) => A)
接著,您知道 map
也應接受 List[Int]
def map[A](f: (Int) => A, xs: List[Int])
最後,你也知道 map
會傳回一個轉換後的 List
,其中包含泛型類型 A
的元素
def map[A](f: (Int) => A, xs: List[Int]): List[A] = ???
這會處理方法簽章。現在你所要做的就是撰寫方法主體。map
方法會將給定的函式套用至給定清單中的每個元素,以產生一個新的轉換清單。執行此操作的方法之一是使用 for
表達式
for (x <- xs) yield f(x)
for x <- xs yield f(x)
for
表達式通常會讓程式碼變得異常簡單,而就我們的目的而言,這最終會成為整個方法主體。
將其與方法簽章結合在一起,現在你有一個獨立的 map
方法,可與 List[Int]
搭配使用
def map[A](f: (Int) => A, xs: List[Int]): List[A] =
for (x <- xs) yield f(x)
def map[A](f: (Int) => A, xs: List[Int]): List[A] =
for x <- xs yield f(x)
讓它成為泛型的
作為一個額外好處,請注意 for
表達式不會執行任何依賴於 List
中類型為 Int
的動作。因此,你可以使用泛型類型參數 B
取代類型簽章中的 Int
def map[A, B](f: (B) => A, xs: List[B]): List[A] =
for (x <- xs) yield f(x)
def map[A, B](f: (B) => A, xs: List[B]): List[A] =
for x <- xs yield f(x)
現在你有一個可與任何 List
搭配使用的 map
方法。
這些範例說明了 map
會如預期般運作
def double(i : Int): Int = i * 2
map(double, List(1, 2, 3)) // List(2, 4, 6)
def strlen(s: String): Int = s.length
map(strlen, List("a", "bb", "ccc")) // List(1, 2, 3)
現在你已經看過如何撰寫將函式作為輸入參數的方法,讓我們來看一下會傳回函式的方法。
此頁面的貢獻者
內容
- 簡介
- Scala 特色
- 為何選擇 Scala 3?
- Scala 體驗
- Hello, World!
- REPL
- 變數和資料類型
- 控制結構
- 網域建模
- 方法
- 一級函式
- 單例物件
- 集合
- 脈絡抽象
- 頂層定義
- 摘要
- 初探類型
- 字串內插
- 控制結構
- 網域建模
- 工具
- OOP 建模
- FP 建模
- 方法
- 方法特色
- Scala 3 中的主要方法
- 摘要
- 函式
- 匿名函式
- 函式變數
- Eta 展開
- 高階函式
- 撰寫您自己的 map 方法
- 建立傳回函式的函式
- 摘要
- 封裝和匯入
- Scala 集合
- 集合類型
- 集合方法
- 摘要
- 函式程式設計
- 什麼是函式程式設計?
- 不可變值
- 純函式
- 函式是值
- 函式錯誤處理
- 摘要
- 類型和類型系統
- 推論類型
- 泛型
- 交集類型
- 聯集類型
- 代數資料類型
- 變異
- 不透明類型
- 結構類型
- 相依函式類型
- 其他類型
- 脈絡抽象
- 擴充方法
- 內容參數
- 內容界線
- 已給予的匯入
- 類型類別
- 多重宇宙等式
- 隱式轉換
- 摘要
- 並行
- Scala 工具
- 使用 sbt 建立和測試 Scala 專案
- 工作表
- 與 Java 互動
- 針對 Java 開發人員的 Scala
- 針對 JavaScript 開發人員的 Scala
- 針對 Python 開發人員的 Scala
- 下一步