解析程序参数的简单方法

时间:2014-07-09 05:51:23

标签: haskell

我已经看到了一些解析程序参数的方法。他们似乎太复杂了。我需要一个简单解决方案。但我也希望能够(最好不一定)通过名称来引用参数。所以,如果命令看起来像这样:

./MyApp --arg1Name arg1Value --arg2Name arg2Value

然后我想将它们视为args["arg1Name"]args["arg2Name"]来获取它们的值。但我知道这不是一个有效的Haskell代码。我现在所拥有的并不多:

main = do
  [args] <- getArgs

我再说一遍,我想要一个简单的解决方案,最好不要涉及任何第三方haskell库。

2 个答案:

答案 0 :(得分:5)

optparse-applicative非常适合参数解析,并且非常易于使用!编写自己的参数解析器将比使用optparse-applicative编写解析器花费10分钟时更难以正确,更改,扩展或以其他方式管理

首先导入Options.Applicative模块。

import Options.Applicative

接下来为命令行配置创建数据类型。

data Configuration = Configuration
                     { foo :: String
                     , bar :: Int
                     }

现在,对于主力,我们使用从optparse-applicative导出的组合器创建解析器。阅读Options.Applicative.Builder上的文档,了解完整体验。

configuration :: Parser Configuration
configuration = Configuration
            <$> strOption
                ( long "foo"
               <> metavar "ARG1"
                )
            <*> option
                ( long "bar"
               <> metavar "ARG2"
                )

现在我们可以在Parser Configuration操作中执行IO来获取命令行数据。

main :: IO ()
main = do 
          config <- execParser (info configuration fullDesc)
          putStrLn (show (bar config) ++ foo config)

我们已经完成了!您可以轻松地扩展此解析器以支持--help参数以打印出使用文档(使用helper <*> configuration创建一个新的解析器并将其传递给info),您可以为某些参数添加默认值(在<> value "default"strOption的参数中包含option子句,您可以支持标志或子解析器或生成制表符完成数据。

图书馆是一种力量倍增器!您在学习优秀图书馆基础知识方面所做的投资将为您所能完成的工作带来好处,而且使用适当的工具比使用&#34;快速&#任务通常更容易(更快!) 34;溶液从胶带中扔出来。

答案 1 :(得分:3)

如何成对解析它们并将它们添加到地图中:

simpleArgsMap :: [String] -> Map String String
simpleArgsMap [] = Map.empty
simpleArgsMap (('-':'-':name):value:rest)
    = Map.insert name value (simpleArgsMap rest)
simpleArgsMap xs = error $ "Couldn't parse arguments: " ++ show xs

一个简单的包装器程序,用于显示此工作:

module Args where

import System.Environment ( getArgs )
import Control.Applicative ( (<$>) )

import qualified Data.Map as Map
import Data.Map ( Map )

main = do
  argsMap <- simpleArgsMap <$> getArgs
  print $ Map.lookup "foo" argsMap