みくにまるのブログ

意識低い系ブロガー、みくにまるが送るブログ。

HaskellでEOFを受け取るまで処理を繰り返すのに苦労したのでメモ

4つの整数の和 | Aizu Online Judge

50 以下の正の整数 n を入力し、0 ~ 9 の範囲の整数 a,b,c,d の組で

a+b+c+d=n

を満たすものの組み合わせ数を出力するプログラムを作成して下さい。

とりあえずパパっと作ったコードがこれ

combinations n = [[a,b,c,d] |a<-[0..9],
                             b<-[0..9],
                             c<-[0..9],
                             d<-[0..9],
                             a+b+c+d==n ]
main = do
  n <- readLn
  print $ length $ combinations n

ところがWrong Answer
試しに手元にテスト用のファイルを作って実験すると
50行ほど入力してみるも1行分の答えしか出力しない。
それではまずい。

単にgetContensするのも面白くないので
EOFを受け取ってから停止するように書き換えてみた

import System.IO

combinations n = [[a,b,c,d] |a<-[0..9],
                             b<-[0..9],
                             c<-[0..9],
                             d<-[0..9],
                             a+b+c+d==n ]
main = do
  n <- getLine
  print $ length $ combinations (read n)
  eof <- isEOF
  if eof then return ()
         else do
           main

EOFを受け取ったら終了
そうでなかったらgetLineを繰り返すプログラムだ。

最初はhIsEOFにして失敗したりで
完成までに丸1日かかってしまった。

参考
haskell - Why isEOF doesn't work? - Stack Overflow
System.IO モジュール(8) isEOF, hIsEOF : tnomuraのブログ
各言語の標準入出力サンプル|CodeIQ│CodeIQ