F# 结合两个序列
F# combining two sequences
我有两个序列,我想以某种方式组合它们,因为我需要将第二个序列的结果打印在第一个序列的旁边。该代码目前是playerItems引用列表的地方:
seq state.player.playerItems
|> Seq.map (fun i -> i.name)
|> Seq.iter (printfn "You have a %s")
seq state.player.playerItems
|> Seq.map (fun i -> i.description) |> Seq.iter (printfn "Description = %s")
目前的结果是
You have a Keycard
You have a Hammer
You have a Wrench
You have a Screw
Description = Swipe to enter
Description = Thump
Description = Grab, Twist, Let go, Repeat
Description = Twisty poke
但是,我需要它
You have a Keycard
Description = Swipe to enter
You have a Hammer
Description = Thump
如有任何帮助,我们将不胜感激。
正如 Foggy Finder 在评论中所说,在你的具体情况下你真的没有两个序列,你有一个序列并且你想为每个项目打印两行,这可以用一个 Seq.iter
像这样:
state.player.playerItems // The "seq" beforehand is not necessary
|> Seq.iter (fun player -> printfn "You have a %s\nDescription = %s" player.name player.description)
不过,我还会告诉您两种组合两个序列的方法,以防您确实确实有两个不同的序列。首先,如果你想把两个序列变成一个元组序列,你会使用 Seq.zip
:
let colors = Seq.ofList ["red"; "green"; "blue"]
let numbers = Seq.ofList [25; 73; 42]
let pairs = Seq.zip colors numbers
printfn "%A" pairs
// Prints: seq [("red", 25); ("green", 73); ("blue", 42)]
如果您想以某种其他方式组合两个序列而不是生成元组,请使用Seq.map2
并向其传递一个双参数函数:
let colors = Seq.ofList ["red"; "green"; "blue"]
let numbers = Seq.ofList [25; 73; 42]
let combined = Seq.map2 (fun clr num -> sprintf "%s: %d" clr num) colors numbers
printfn "%A" combined
// Prints: seq ["red: 25"; "green: 73"; "blue: 42"]
最后,如果您只想对两个序列中的每对项目执行一些副作用,那么 Seq.iter2
就是您的朋友:
let colors = Seq.ofList ["red"; "green"; "blue"]
let numbers = Seq.ofList [25; 73; 42]
Seq.iter2 (fun clr num -> printfn "%s: %d" clr num)
这会将以下三行打印到控制台:
red: 25
green: 73
blue: 42
请注意,在 Seq.iter
函数中,我没有存储结果。那是因为 Seq.iter
的结果始终是 ()
,"unit" 值相当于 F# 中的 void
。 (除了它比 void
有用得多之外,原因超出了这个答案的范围。在 Stack Overflow 中搜索“[F#] unit”,你应该会找到一些有趣的问题和答案,比如 this one.
我有两个序列,我想以某种方式组合它们,因为我需要将第二个序列的结果打印在第一个序列的旁边。该代码目前是playerItems引用列表的地方:
seq state.player.playerItems
|> Seq.map (fun i -> i.name)
|> Seq.iter (printfn "You have a %s")
seq state.player.playerItems
|> Seq.map (fun i -> i.description) |> Seq.iter (printfn "Description = %s")
目前的结果是
You have a Keycard
You have a Hammer
You have a Wrench
You have a Screw
Description = Swipe to enter
Description = Thump
Description = Grab, Twist, Let go, Repeat
Description = Twisty poke
但是,我需要它
You have a Keycard
Description = Swipe to enter
You have a Hammer
Description = Thump
如有任何帮助,我们将不胜感激。
正如 Foggy Finder 在评论中所说,在你的具体情况下你真的没有两个序列,你有一个序列并且你想为每个项目打印两行,这可以用一个 Seq.iter
像这样:
state.player.playerItems // The "seq" beforehand is not necessary
|> Seq.iter (fun player -> printfn "You have a %s\nDescription = %s" player.name player.description)
不过,我还会告诉您两种组合两个序列的方法,以防您确实确实有两个不同的序列。首先,如果你想把两个序列变成一个元组序列,你会使用 Seq.zip
:
let colors = Seq.ofList ["red"; "green"; "blue"]
let numbers = Seq.ofList [25; 73; 42]
let pairs = Seq.zip colors numbers
printfn "%A" pairs
// Prints: seq [("red", 25); ("green", 73); ("blue", 42)]
如果您想以某种其他方式组合两个序列而不是生成元组,请使用Seq.map2
并向其传递一个双参数函数:
let colors = Seq.ofList ["red"; "green"; "blue"]
let numbers = Seq.ofList [25; 73; 42]
let combined = Seq.map2 (fun clr num -> sprintf "%s: %d" clr num) colors numbers
printfn "%A" combined
// Prints: seq ["red: 25"; "green: 73"; "blue: 42"]
最后,如果您只想对两个序列中的每对项目执行一些副作用,那么 Seq.iter2
就是您的朋友:
let colors = Seq.ofList ["red"; "green"; "blue"]
let numbers = Seq.ofList [25; 73; 42]
Seq.iter2 (fun clr num -> printfn "%s: %d" clr num)
这会将以下三行打印到控制台:
red: 25
green: 73
blue: 42
请注意,在 Seq.iter
函数中,我没有存储结果。那是因为 Seq.iter
的结果始终是 ()
,"unit" 值相当于 F# 中的 void
。 (除了它比 void
有用得多之外,原因超出了这个答案的范围。在 Stack Overflow 中搜索“[F#] unit”,你应该会找到一些有趣的问题和答案,比如 this one.