我想寫一個函式,該函式將接受一個字串和一個字符,并隨機地將字符預置或追加到字串中。
我是這樣寫的,但它不作業,因為有些型別的簽名是在最后一行:
join :: RandomGen g => [Char] -> Char -> g -> ([Char], g)
join letters g = if inverse
then (letter:letters, newG)
else (letters [letter], newG)
where (inverse, newG) = random g :: (Bool, RandomGen)
我得到的錯誤是:
- Expecting one more argument to 'RandomGen'
期待一個型別,但'RandomGen'有種類'* -> Constraint'/span>
- 在運算式型別簽名:(Bool, RandomGen)
在運算式: random g :: (Bool, RandomGen)
在一個模式系結。
(inverse, newG) = random g :: (Bool, RandomGen)
那么我如何正確地生成一個布林值并從函式中回傳新的生成器呢?
uj5u.com熱心網友回復:
random g的型別不是(Bool, RandomGen),因為RandomGen是一個typeeclass,不是一個型別。
我們可以通過一個型別應用來指定inverse的型別,從而實作為:
{-# LANGUAGE TypeApplication #-}
join :: RandomGen g => [Char] -> Char -> g -> ([Char], g)
join letters g
| 反轉 = (letter:字母, newG)
| 否則 = (letter [letter], newG)
where (inverse, newG) = random @Bool g
這就是說,由于inverse是由一個衛兵(或if ... then ... else ... )使用的,編譯器知道inverse是一個Bool,因此它可以算出inverse和newG的型別。因此,只需將join定義為:
join :: RandomGen g => [Char] -> Char -> g -> ([Char], g)
join letters g
| 反轉 = (letter:字母, newG)
| 否則 = (letter [letter], newG)
where (inverse, newG) = random g
使用另一個名字也可能比join更好,因為join :: monad m => m (m a) -> m a是一個在處理monad時經常使用的函式。
轉載請註明出處,本文鏈接:https://www.uj5u.com/qianduan/329815.html
標籤:
