我创建了这个数据类型和函数:
type Bit = Int
randomFloatList :: Int -> [Float]
randomFloatList seed = randoms (mkStdGen seed)
我想创建一个使用zipWith
. 该函数有一个seed
作为用于 的参数randomFloatList
,如果随机元素介于 0 和噪声之间,则该位会更改。我正在尝试这样做,但我遇到了困难zipWith
:
谢谢。
我创建了这个数据类型和函数:
type Bit = Int
randomFloatList :: Int -> [Float]
randomFloatList seed = randoms (mkStdGen seed)
我想创建一个使用zipWith
. 该函数有一个seed
作为用于 的参数randomFloatList
,如果随机元素介于 0 和噪声之间,则该位会更改。我正在尝试这样做,但我遇到了困难zipWith
:
谢谢。
我相信您想获取Bit
s 列表并使用随机列表来决定是否更改原始列表。(如果不是,请澄清。)
channel :: Int -> Float -> [Bit] -> [Bit]
channel seed noise xs = zipWith (alterBit noise) (randomFloatList seed) xs
请注意,您不需要某些括号 - 您不需要用于函数应用的括号,仅用于分组。
alterBit :: Float -> Float -> Bit -> Bit
alterBit noise random bit | random <= noise = alter bit
| otherwise = bit
同样,我已经删除了对我正在使用它的列表的任何引用 -zipWith
将把这个函数从浮点数和位列表中发送它需要的单个元素。
我冒昧地定义
data Bit = O | I deriving Show
并且只能想到一个改变功能:
alter :: Bit -> Bit
alter O = I
alter I = O
让我们测试一下:
> take 6 $ randomFloatList 3
[0.10321328,0.98988104,0.46191382,0.8553592,0.7980472,0.35561606]
> map (<= 0.5) $ take 6 $ randomFloatList 3
[True,False,True,False,False,True]
> channel 3 0.5 [O,O,O,O,O,O]
[I,O,I,O,O,I]
是的,这改变了它应该的那些。
zipWith
的签名是(a -> b -> c) -> [a] -> [b] -> [c]
。这意味着它对于映射一个在两个列表上接受两个参数的函数很有用。
我认为,在您的情况下,您只想将一个函数映射到一个列表上(因为您的函数alterBit
只接受一个参数),所以您必须使用map
,而不是zipWith
.
另请注意seed
,除非您将它们定义为模块中的常量或将它们显式传递noise
给.alterBit
alterBit