ReplicateM
中Haskell
(F#
)是否有任何等效函数?
示例:
replicateM 2 [1,2,3] =
[[1,1],[1,2],[1,3],[2,1],[2,2],[2,3],[3,1],[3,2],[3,3]]
答案 0 :(得分:4)
您可以在F#+中找到它,并为List
和Seq
定义:
#r @"C:\packages\FsControl.2.0.0-CI00073\lib\net40\FsControl.dll"
#r @"C:\packages\FSharpPlus.1.0.0-CI00015\lib\net40\FSharpPlus.dll"
open FSharpPlus
List.replicateM 2 [1;2;3]
// val it : List<int list> =
// [[1; 1]; [1; 2]; [1; 3]; [2; 1]; [2; 2]; [2; 3]; [3; 1]; [3; 2]; [3; 3]]
Seq.replicateM 2 [1;2;3]
// val it : seq<int> list =
// [seq [1; 1]; seq [1; 2]; seq [1; 3]; seq [2; 1]; seq [2; 2]; seq [2; 3];
// seq [3; 1]; seq [3; 2]; seq [3; 3]]
如果您正在从Haskell进行翻译,那么有一个带有该函数和其他Haskell绑定的Compatibility.Haskell模块。
事实上,最后一个参数可以是列表或任何其他Applicative,但如果您不想使用该库,并且您对仅适用于list
的版本感到满意,那么您可以像这样定义:
let replicateM n x =
let k m m' = List.collect (fun x ->
List.collect(fun xs ->
[List.Cons(x,xs)]) m') m
List.foldBack k (List.replicate n x) [[]]
答案 1 :(得分:1)
该功能在标准库中不可用,因此如果您不想依赖外部库,则需要自己编写。最简单的实现如下:
let rec replicateM m l = seq {
if m = 1 then
// If we want just one replication, generate singleton lists
for v in l do yield [v]
else
// Otherwise, iterate over all lists with m-1 replicates
for s in replicateM (m - 1) l do
// .. and append elements from 'l' to the front
for v in l do yield v::s }