ビンゴの結果を整形表示
Posted feedbacks - Haskell
showBingoがビンゴの整数リストを文字列に変換する 関数。第一引数は数字の最大桁数 shuffle は前回と同じだけど再掲
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 | module Main (main) where
import Data.List
import System.Environment
import System.Random
import Text.Printf
shuffle :: [a] -> StdGen -> Int -> [a] -> [a]
shuffle acc _ 0 _ = acc
shuffle acc g n xs = case randomR (0,n-1) g of
(i,g') -> case splitAt i xs of
(ys,z:zs) -> shuffle (z:acc) g' (n-1) (ys++zs)
main :: IO ()
main = do { x:_ <- getArgs
; g0 <- getStdGen
; let n = read x
; putStr $ showBingo (length x)
$ shuffle [] g0 n [1..n]
}
showBingo :: Int -> [Int] -> String
showBingo w = unlines . map (showLines w) . map unzip . slice 10 . zip [1..]
slice :: Int -> [a] -> [[a]]
slice n = unfoldr phi
where phi [] = Nothing
phi xs = Just $ splitAt n xs
showLines :: Int -> ([Int],[Int]) -> String
showLines n (xs,ys) = unlines [ unwords $ map (pr n) xs
, unwords $ map (pr n) ys]
pr :: Int -> Int -> String
pr w = printf $ "%"++show w++"d"
{-
% ./bingo 30
1 2 3 4 5 6 7 8 9 10
19 26 2 6 11 17 23 8 7 5
11 12 13 14 15 16 17 18 19 20
18 13 16 12 22 24 4 21 1 25
21 22 23 24 25 26 27 28 29 30
3 29 10 27 15 9 28 14 20 30
% ./bingo 35
1 2 3 4 5 6 7 8 9 10
20 32 18 3 29 13 33 1 24 21
11 12 13 14 15 16 17 18 19 20
17 12 34 4 25 8 31 30 14 35
21 22 23 24 25 26 27 28 29 30
10 11 7 16 19 15 23 27 9 22
31 32 33 34 35
2 28 5 6 26
-}
|
ちょっとゴチャゴチャしてる。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 | import Random (randomRIO)
import Data.List ((\\),elemIndex)
import Data.Maybe (fromJust)
import Control.Monad (zipWithM_)
bingo :: Int -> IO [Int]
bingo n = b [1..n] n []
where b [] n ret = return ret
b xs (n+1) ret = do
r <- randomRIO (0,n)
let m = xs !! r in b (xs \\ [m]) n (ret ++ [m])
showBingo :: Int -> IO ()
showBingo n = bingo n >>= \xs -> zipWithM_ printBingo (f idxs) (f (t xs))
where idxs = [1..n]
f = map concat . map u . s
s xs = if xs == [] then [] else let (h,t) = splitAt 10 xs in h:s t
t xs = map ((1+) . fromJust . (\x -> x `elemIndex` idxs)) xs
u xs = let len = length (show n) in map (surpress (len + 1) . show) xs
surpress n xs = reverse $ take n $ reverse xs ++ cycle " "
printBingo x y = putStrLn x >> putStrLn y >> putStrLn ""
|



raynstard
#3403()
Rating1/1=1.00
「重複無し乱数」で作ったbingo関数の結果を下のように「何番目の乱数か」とセットにして10個ずつ折り返して表示するコードを書いてください。
[ reply ]