あなたの主な問題は、あなたがまだ命令的であると考えているようです(を使用insert
)-()
値の単位でもあります-おそらく代わりに(空のリスト)を書きたかったのです[]
が、それでもxs
ここは完全に定義されていないため、これも修正する必要があります(正直に言うとわかりません)。
完全数
私はそこに基本的なアイデアを見ることができると思います.これを修正する最善の方法は、完全なリスト理解を行うことだと思います.
listX n = [ x | x <- [1..n], sum [ y | y <- [1..x-1], x `mod` y == 0] == x]
ご覧のとおり、これを少し変更しました。最初にx
から1
までのすべてn
が完全かどうかをチェックします。これは、すべての適切な約数を合計し、合計が等しいかどうかをチェックすることによって行いますx
(これが部分の仕事ですsum [...] == x
) 。 - リスト内包表記にガードを追加できるため、これが機能することを知らない場合に備えて (これが true であるsum [..] == x
すべての値を除外します)。x
より良いバージョン
これをもう少し読みやすくする (そして懸念事項を分離する) ために、次のように書くことをお勧めします。
properDivisors :: Integer -> [Integer]
properDivisors n = [ d | d <- [1..n-1], n `mod` d == 0]
isPerfect :: Integer -> Bool
isPerfect n = sum (properDivisors n) == n
perfectNumbers :: [Integer]
perfectNumbers = filter isPerfect [1..]
perfectNumbersUpTo :: Integer -> [Integer]
perfectNumbersUpTo n = takeWhile (<= n) perfectNumbers