0

「xxxxyzz」などの文字列を解析しているため、文字が「x」の場合は、出力を行い、同時にリストを変更する必要があります。以下のコードは

import Data.Char
output l = zipWith (+) rr ll
            where
              out = foldl
                        ( \ (c,a) e ->
                               case c of
                                'x' -> chr c!!0 --output first element of the list
                                       ([1]++tail(c),a) ) -- add [1] to the c list
                        ([0,0,0,0,0],[0,0,0,0,0])
              (ll,rr) = out l 
4

2 に答える 2

1

次のようなものを書くことができます(お勧めしません)

output'' :: String -> IO String
output'' = fmap reverse . foldM parseChar []
  where parseChar xs 'x' = putStrLn "'x' to upper" >> return ('X':xs)
        parseChar xs 'y' = putStrLn "'y' to 'W'"   >> return ('W':xs)
        parseChar xs  x  = putStrLn "no transform" >> return ( x :xs)

出力あり

*Main> output'' "xyz"
'x' to upper
'y' to 'W'
no transform
"XWz"

しかし、For a Few Monad Moreから(Learn You a Haskell for Great Good!)

次のように書くことができます:

import Control.Monad.Writer

output :: String -> Writer [String] String
output [] = return []
output (x:xs) = do
  xs' <- output xs
  x'  <- case x of
         'x' -> tell ["'x' to upper"] >> return 'X'
         'y' -> tell ["'y' to 'W'"]   >> return 'W'
         _   -> tell ["no transform"] >> return x
  return (x':xs')

モナドを使用するとより柔軟になり、Writer を使用するとコードを純粋に実行できます (純粋であり、モナドのコンテキストとデータを処理する方法を制御できます。直接 IOoutput''関数では制御できません)。

output次のように関数を不純なコードに使用できます

main = do
  input <- getLine
  let (result, logging) = runWriter $ output input
  putStrLn $ "Result: " ++ result
  putStrLn $ unlines logging

実行中の出力は

*Main> main
hxdynx
Result: hXdWnX
'x' to upper
no transform
'y' to 'W'
no transform
'x' to upper
no transform

モナドを「foldM」のようなモナド関数と組み合わせることができます。

output' :: String -> Writer [String] String
output' = fmap reverse . foldM parseChar []
  where parseChar xs 'x' = tell ["'x' to upper"] >> return ('X':xs)
        parseChar xs 'y' = tell ["'y' to 'W'"]   >> return ('W':xs)
        parseChar xs  x  = tell ["no transform"] >> return ( x :xs)

(対数配列が逆)

于 2012-12-04T08:10:07.070 に答える
0

Haskell では、モナドを使わずに実行順序を予測することはできません。手始めに、 のdoブロックでいくつかのテストを行っmainてから、別の関数として書き直すことをお勧めします。

Haskell の IO の概念をよく理解しておくとよいでしょう: http://www.haskell.org/onlinereport/haskell2010/haskellch7.html#x14-1420007

于 2012-12-04T20:53:13.843 に答える