内容简介:F# 的 List module 提供眾多本文探討英文字母 G ~ P 開頭的 function。macOS High Sierra 10.13.3
F# 的 List module 提供眾多 List
常用的 Higher Order Function,要能發揮 FP 的威力,首先必須能活用內建 function。
本文探討英文字母 G ~ P 開頭的 function。
Version
macOS High Sierra 10.13.3
.NET Core SDK 2.1.101
JetBrains Rider 2017.3.1
F# 4.1
List.head
傳回 list 第一個 element,相當於 list 的 Head
property
list : 'T list -> 'T
[ 1; 2; 3 ] |> List.head |> printf "%d" // 1
List.indexed
將 element 的 key 與 value 封裝成 tuple,以 list 回傳
list : 'T list -> (int * 'T) list
[ 1; 2; 3 ] |> List.indexed |> printf "%A" // [(0, 1); (1, 2); (2, 3)]
List.init
根據 index 值建立新的 list
int -> initializer : (int -> 'T) -> 'T list
List.init 10 (fun idx -> idx * 2) |> printf "%A" // [0; 2; 4; 6; 8; 10; 12; 14; 16; 18]
List.isEmpty
判斷 list 是否為空,相當於 list 的 IsEmpty
property
list : 'T list -> bool
[] |> List.isEmpty |> printf "%b" // true
List.item
傳回指定 index 的 element 值,相當於 list 的 Item
property
index : int -> list : 'T list -> 'T
[ 1; 2; 3 ] |> List.item 2 |> printf "%d" // 3
List.iter
對每個 element 執行回傳值為 unit
的 action function
action : ('T -> unit) -> list : 'T list -> unit
[ 1; 2; 3 ] |> List.iter (printf "%A ") // 1 2 3
List.iter2
同時對兩個 list 的每個 element 執行回傳值為 unit
的 action function
action : ('T1 -> 'T2 -> unit) -> list1 : 'T1 list -> list2 : 'T2 list -> unit
let list1 = [ 1; 2; 3 ]
let list2 = [ 4; 5; 6 ]
let action elm1 elm2 =
printf "%d " (elm1 + elm2)
List.iter2 action list1 list2
// 5 7 9
List.iteri
對每個 element 執行回傳值為 unit
的 action function,但會將 index 也傳入 action function
action : (int -> 'T -> unit) -> list : 'T list -> unit
[ 1 .. 3 ] |> List.iteri (fun idx elm -> printfn "%d : %d" idx elm) // 0 : 1 // 1 : 2 // 2 : 3
List.iteri2
同時對兩個 list 的每個 element 執行回傳值為 unit
的 action function,但會將 index 也傳入 action function
action : (int -> 'T1 -> 'T2 -> unit) -> list1 : 'T1 list -> list2 : 'T2 list -> unit
let list1 = [ 1; 2; 3 ]
let list2 = [ 4; 5; 6 ]
let action idx elm1 elm2 =
printfn "%d : %d" idx (elm1 + elm2)
List.iteri2 action list1 list2
// 0 : 5
// 1 : 7
// 2 : 9
List.last
傳回 list 最後一個 element
list : 'T list -> 'T
[ 1; 2; 3 ] |> List.last |> printf "%d" // 3
List.length
傳回 list 的 element 個數,相當於 list 的 Length
property
list: 'T list -> int
[ 1; 2; 3 ] |> List.length |> printf "%d" // 3
List.map
將 list 的每個 element 根據 mapping function 轉換成另外一個 value 的 list
mapping : ('T -> 'U) -> list : 'T list -> 'U list
[ 1; 2; 3 ] |> List.map (fun elm -> elm * elm) |> printf "%A" // [1; 4; 9]
若經過 mapping function 後 element 個數不一樣,請用 List.collect()
List.map2
將兩個 list 的每個 element 根據 mapping function 轉換成另外一個 value 的 list
mapping : ('T1 -> 'T2 -> 'U) -> list1 : 'T1 list -> list2 : 'T2 list -> 'U list
let list1 = [ 1; 2; 3 ] let list2 = [ 4; 5; 6 ] List.map2 (fun elem1 elem2 -> elem1 + elem2) list1 list2 |> printf "%A" // [5; 7; 9]
List.map3
將三個 list 的每個 element 根據 mapping function 轉換成另外一個 value 的 list
mapping : ('T1 -> 'T2 -> 'T3 -> 'U) -> list1 : 'T1 list -> list2 : 'T2 list -> list3 : 'T3 list -> 'U list
let list1 = [ 1; 2; 3 ] let list2 = [ 4; 5; 6 ] let list3 = [ 7; 8; 9 ] List.map3 (fun elm1 elm2 elm3 -> elm1 + elm2 + elm3) list1 list2 list3 |> printf "%A" // [12; 15; 18]
List.mapFold
相當於 List.map()
+ List.fold()
合體,回傳為 tuple。
mapping : ('State -> 'T -> 'Result * 'State) -> state : 'State -> list : 'T list -> 'Result list * 'State
[ 1; 2; 3 ] |> List.mapFold (fun acc elm -> (elm * elm , acc + elm * elm)) 0 |> printf "%A" // ([1; 4; 9], 14)
mapping funciton 中,回傳的是 tuple。
-
第 1 個 element 為
List.map()的結果 -
第 2 個 element 為
List.fold()的結果
List.mapFoldBack
相當於 List.map()
+ List.fold()
合體,回傳為 tuple,但從 list 的尾部開始,signature 的順序也不一樣
mapping : ('T -> 'State -> 'Result * 'State) -> list : 'T list -> state : 'State -> 'Result * 'State
let list1 = [ 1; 2; 3 ] List.mapFoldBack (fun elm acc -> (elm * elm , acc + elm * elm)) list1 0 |> printf "%A" // ([1; 4; 9], 14)
List.mapi
對 list 的每個 element 根據 mapping function 轉換成另外一個 value 的 list,但會將 index 也傳入 mapping function
mapping : (int -> 'T -> 'U) -> list : 'T list -> 'U list
[ 1; 2; 3 ] |> List.mapi (fun idx elm -> idx * elm) |> printf "%A" // [0; 2; 6]
List.mapi2
同時對兩個 list 的每個 element 根據 mapping function 轉換成另外一個 value 的 list,但會將 index 也傳入 mapping function
let list1 = [ 1; 2; 3 ]
let list2 = [ 4; 5; 6 ]
let mapping idx elm1 elm2 =
idx + elm1 + elm2
List.mapi2 mapping list1 list2
|> printf "%A"
// [5; 8; 11]
List.max
傳回 list 內最大的值
list : 'T list -> 'T
[ 1; 2; 3 ] |> List.max |> printf "%d" // 3
List.maxBy
傳回 list 內的最大值,但所比較的是經過 projection function 轉換過的值
project : ('T -> 'U) -> list : 'T list -> 'T
[ 1; 2; 3 ] |> List.maxBy (fun elm -> 1 - elm) |> printf "%d" // 1
[1; 2; 3]
經過 projection function 後為 [0; -1; -2]
,所以最大值為 0
,但 List.maxBy()
回傳的是原 list 的值,所以為 1
。
Projection function 的值只是比較用,不是回傳用
List.min
傳回 list 內最小的值
list : 'T list -> 'T
[ 1; 2; 3 ] |> List.min |> printf "%d" // 1
List.minBy
傳回 list 內的最小值,但所比較的是經過 projection function 轉換過的值
project : ('T -> 'U) -> list : 'T list -> 'T
[ 1; 2; 3 ] |> List.minBy (fun elm -> 1 - elm) |> printf "%d" // 3
[1; 2; 3]
經過 projection function 後為 [0; -1; -2]
,所以最小值為 0
,但 List.minBy()
回傳的是原 list 的值,所以為 3
。
Projection function 的值只是比較用,不是回傳用
List.ofArray
由 array 轉成 list
array : 'T [] -> 'T list
[| 1; 2; 3 |] |> List.ofArray |> printf "%A" // [1; 2; 3]
List.ofSeq
由 sequence 轉成 list
source : seq<'T> -> 'T list
seq { 1 .. 5 }
|> List.ofSeq
|> printf "%A"
// [1; 2; 3; 4; 5]
List.pairWise
根據 list 順序,回傳兩兩成為 tuple 的 list
list : 'T list -> ('T * 'T) list
[ 1; 2; 3; 4 ] |> List.pairwise |> printf "%A" //[(1, 2); (2, 3); (3, 4)]
List.partition
將 list 根據 predicate function 拆成兩個 list,同時放在一個 tuple 中傳回
predicate : ('T -> bool) -> list : 'T list -> 'T list * 'T list
[ 1 .. 10 ] |> List.partition (fun elm -> elm % 2 = 0) |> printf "%A" // ([2; 4; 6; 8; 10], [1; 3; 5; 7; 9])
List.permute
List 重新根據 indexMap function 的規則,重新調整 element 順序
indexMap : (int -> int) -> list : 'T list -> 'T list
[ 1; 2; 3 ] |> List.permute (fun idx -> (idx + 1) % 3) |> printf "%A" // [3; 1; 2]
List.pick
找出符合 chooser function 條件的第一個 element
chooser : ('T -> 'U option) -> list : 'T list -> -> 'U
let chooser elm =
match elm with
| elm when elm % 2 = 0 -> Some elm
| _ -> None
[ 1; 2; 3 ]
|> List.pick chooser
|> printf "%A"
// 2
若找不到 element,會拋出 KeyNotFoundException : An index satisfying the predicate was not found in the collection.
Q: List.find()
與 List.pick()
有何差異?
相同
-
都用來找資料
-
找不到資料都會拋出
KeyNotFoundException
相異
-
List.find()的 predicate function 為'T -> bool -
List.pick()的 chooser function 為'T -> 'U option
若 fuction 回傳為 option
,則適合用 List.pick()
,否則使用 List.find()
Conclusion
- List module 所提供的 function 都必須非常熟練,因為這些都是常用的 Higher Order Function,算是 FP 的基本功
Reference
以上所述就是小编给大家介绍的《深入探討 List Module 所提供的 Function (G ~ P)》,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对 码农网 的支持!
猜你喜欢:- 深入探討 F# List Module 所提供的 Function (Q ~ Z)
- 深入探討 List Module 所提供的 Function Part I (A ~ F)
- 能快速提供一个子环境吗?
- 提供一个排查性能问题的思路
- 创新中关村报道称 Cocos 开发者沙龙为开发者、技术提供者等提供了交流合作平台
- C/C++ 提供 Python 接口
本站部分资源来源于网络,本站转载出于传递更多信息之目的,版权归原作者或者来源机构所有,如转载稿涉及版权问题,请联系我们。
Head First Web Design
Ethan Watrall、Jeff Siarto / O’Reilly Media, Inc. / 2009-01-02 / USD 49.99
Want to know how to make your pages look beautiful, communicate your message effectively, guide visitors through your website with ease, and get everything approved by the accessibility and usability ......一起来看看 《Head First Web Design》 这本书的介绍吧!