如何将Haskell System.Directory getHomeDirectory转换为常规字符串?

时间:2013-03-12 15:02:59

标签: haskell xmonad

我是Haskell noob,目前只使用它来配置xmonad。

我想将我的配置放入git仓库,因为我不想硬编码我的家庭目录来抓取我的图标。

我检查了一下 http://www.haskell.org/haskellwiki/How_to_get_rid_of_IO 但是我太无知了解它。

hd h = h =<< getHomeDirectory

getIcon::String -> String
getIcon out = ( "^i("++hd++".xmonad/dzen2/"++out )

这实际上可行吗?如果是这样,怎么样? 我不想在目录上操作,我只想要路径,作为一个字符串,它杀了我。

错误是:

Couldn't match expected type `[Char]'
            with actual type `(FilePath -> IO b0) -> IO b0'
In the first argument of `(++)', namely `hd'
In the second argument of `(++)', namely
  `hd ++ ".xmonad/dzen2/" ++ out'
In the expression: ("^i(" ++ hd ++ ".xmonad/dzen2/" ++ out)

在我看来,IO monad根本没有删除。

更新: 好的。我将学习如何适应IO规则,在此之前我将保持硬编码并使用将替换相应位的脚本克隆配置文件。

4 个答案:

答案 0 :(得分:5)

您的getIcon类型错误,因为getHomeDirectory执行IO:

getIcon :: String -> IO String
getIcon out = do
     hd <- getHomeDirectory
     return $ "^i(" ++ hd ++ ".xmonad/dzen2/" ++ out

请记住,Haskell通过类型IO区分具有副作用的代码 - 例如读取硬盘。

所以调用者也会在IO中:

main = do
    s <- getIcon "foo"
    .. now you have a regular string 's' ...

答案 1 :(得分:1)

您可以在调用getIcon时更改代码吗?

如果您在调用之前可以获取主目录,则可以执行

getIcon :: String -> String -> String
getIcon out hd = ( "^i("++hd++".xmonad/dzen2/"++out )

然后你在哪里打电话(假设它也在IO

someIOFunction = do
    things
    ....
    hd <- getHomeDirectory
    getIcon out hd

只是指出最后的手段,如果没有其他工作,有unsafePerformIO,但我从来没有真正使用它(我觉得它通常不赞成),所以我不能在那里帮助你太多了。

答案 2 :(得分:1)

你可以“突破”其他monad,但你不能突破IO monad。您的Xmonad配置文件中的内容可能是您想要的:

getIcon::String -> String
getIcon out = ( "^i("++hd++".xmonad/dzen2/"++out )

main =
   h <- getHomeDirectory
   let myIcon = getIcon "Firefox"
   xmonad $ desktopConfig . . . -- use myIcon somewhere in this expression

答案 3 :(得分:0)

使用Template Haskell可以在编译时解包某些IO值。一个人的主目录是一个合理的候选人,因为它不会经常变化。用于在编译时将主目录作为字符串获取的模板Haskell解决方案可能编码如下:

{-# LANGUAGE TemplateHaskell #-}
module HomeDirectory where

import Language.Haskell.TH
import System.Directory

myHome :: String
myHome = $(LitE . StringL `fmap` runIO getHomeDirectory)

请注意,模板Haskell是一个臭名昭着的棘手野兽。这个例子很简单,但很容易让人感到复杂和困惑。