2016-07-26 30 views
7

我有这样一个功能:我的Haskell程序是懒得

type App a = ExceptT AppError (ResourceT IO) 

onEvent :: SDL.EventPayload -> App() 
onEvent event = do 
    liftIO $ putStrLn "EVE!" 
    case event of 
    SDL.MouseMotionEvent dat -> do 
     liftIO $ putStrLn "HELLO" 
    SDL.KeyboardEvent kbe -> liftIO $ putStrLn "WORLD" 
    _ -> return() 

这就是我的应用程序正在使用回调。

这个函数看起来不会触发,因为putStrLn没有打印到控制台。

不过这个功能 - 与轻微的修改确实都打印到控制台:

onEvent :: SDL.EventPayload -> App() 
onEvent event = do 
    liftIO $ putStrLn "EVE!" 
    case event of 
    SDL.MouseMotionEvent dat -> do 
     liftIO $ print dat 
    SDL.KeyboardEvent kbe -> liftIO $ print kbe 
    _ -> return() 

为什么的SDL.EventPayload引起周围putStrLn的全面评估工作?

如何让我的函数回调更可靠?

+6

你确定这ISN不仅仅是一个缓冲问题?改为使用'hPutStrLn stderr'。 –

+0

@ ThomasM.DuBuisson是的,它只是一个缓冲问题!现在我觉得有点傻... –

+0

Bah,没有感觉愚蠢。这是一个公平的问题。很高兴的事情正在工作。 –

回答

1

由于Thomas在评论中指出,这看起来像一个缓冲问题。 System.IO包描述标准buffering behavior

关于如何解决此类问题,您有几个选项。您可以在程序中手动设置缓冲模式:

hSetBuffering stdout NoBuffering 

在函数的开头。这将关闭所有缓冲(您也可以选择LineBuffering)并立即打印到标准输出。

您还可以刷新缓冲区,每次打印后:

SDL.MouseMotionEvent dat -> do 
    liftIO $ putStrLn "HELLO" 
    hFlush stdout 

或者你可以尝试直接打印到stderr手柄具有不同的默认缓冲规则:

SDL.MouseMotionEvent dat -> do 
    liftIO $ hPutStrLn stderr "HELLO"