zipWith(++)任意数量的列表

Alb*_*ani 1 haskell

我必须用(++)压缩n个列表.我发现在列表上定义此运算符没有更好的方法:

 (+++) = zipWith (\x y -> x ++ " " ++ y)
Run Code Online (Sandbox Code Playgroud)

还有更好的解决方案吗?

在Markus1189回答之后,我提出了一个更普遍的问题:确实存在这样的函数:

zipNWith f2 [a] = f2 (f2 x1 x2) x3 ... f2 (xn-2 xn-1) xn?
Run Code Online (Sandbox Code Playgroud)

这是运算符使用的程序(+++)

csoundLines instrs inits durs amps freqs = putStrLn . unlines $
    repeat "i" +++ ms instrs +++ ms inits +++ ms durs +++ ms amps +++ ms freqs
  where
  (+++) = zipWith (\x y -> x ++ " " ++ y)
  ms xs = map show xs

scaleNTonic n = map (\i -> 440 * 2 ** (i/n)) [0..n]
Run Code Online (Sandbox Code Playgroud)

- 示例:csoundLines(重复1)[0.5,1 ...](重复0.5)(重复0.3)$ scaleNTonic 6

> i 1 0.5 0.5 0.3 440.0
> i 1 1.0 0.5 0.3 493.8833012561241
> i 1 1.5 0.5 0.3 554.3652619537442
> i 1 2.0 0.5 0.3 622.2539674441618
> i 1 2.5 0.5 0.3 698.4564628660078
> i 1 3.0 0.5 0.3 783.9908719634985
> i 1 3.5 0.5 0.3 880.0
Run Code Online (Sandbox Code Playgroud)

Dan*_*rro 6

您还可以将折叠用于任意数量的列表:

>>> foldr1 (zipWith (++)) [["dog","cat"],["cat","dog"],["rat","rat"]]
["dogcatrat","catdograt"]
Run Code Online (Sandbox Code Playgroud)

或者中间有空格:

>>> foldr1 (zipWith (\x y -> x ++ " " ++ y)) [["dog","cat"],["cat","dog"],["rat","rat"]]
["dog cat rat","cat dog rat"]
Run Code Online (Sandbox Code Playgroud)


Yuu*_*uri 5

处理任意数量的列表的最简单方法是将它们全部放在列表中:

import Data.List
zipAll :: [[String]] -> [String]
zipAll = map unwords . transpose

ghci> zipAll [["a", "b", "c"], ["1", "2", "3"], ["xx", "yy", "zz"]]
["a 1 xx","b 2 yy","c 3 zz"]
Run Code Online (Sandbox Code Playgroud)

我不确定是否有一种简单的方法可以将它们作为单独的参数传递(这个数字是未定义的),但是你可以使用printf的方法.

  • `transpose`适用于无限列表,结果也是无限的,你可以"获取"所需数量的元素,例如输入列表的最小长度. (2认同)