从字符串解析命令行开关和args的惯用clojure [英] Idiomatic clojure to parse command line switches and args from string

查看:73
本文介绍了从字符串解析命令行开关和args的惯用clojure的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我想解析命令行字符串,并将任何命令开关与其后续参数分组。例如:

I'd like to parse a command line string, and group any command switches with their subsequent arguments. So, for example:

(parse "git branch -d f1 f2 -a -m message") => 
[["-d" "f1" "f2"]["-a"]["-m" "message"]]

我忽略了切换后不会立即出现的参数。

I ignore args not immediately following a switch.

我写的代码如下:

(defn switch? [s] (re-find #"\-+" s))
(defn tokenify [s] (clojure.string/split s #" "))
(defn parse [cmd-str]
  (loop [lst (tokenify cmd-str), acc [], _acc []]
    (let [fs (first lst), rs (rest lst), new? (empty? _acc)]
      (cond (empty? lst) (if new? acc (conj acc _acc))
            (switch? fs) (if new?
                           (recur rs acc (conj _acc fs))
                           (recur rs (conj acc _acc) (conj [] fs)))
            :else (if new?
                    (recur rs acc _acc)
                    (recur rs acc (conj _acc fs)))))))

这可行,但它是相当低的水平和可怕。有没有一个简单的方法使用reduce或partition或group-by,这将使同样的功能更清洁和更成语?

That works, but it's pretty low level and horrible. Is there a simple way using reduce or partition or group-by that would make the same functionality a lot cleaner and more idiomatic?

推荐答案

以下是使用 clojure.tools.cli 的基本概述

(def command-line-spec
  [["-m" "--mode 0|1" "description of option that takes 1 or 0"
    :parse-fn #(case (s/lower-case %)
                 ("1" "true" "create") :one
                 ("0" "false" "destroy") :zero
                 :invalid)
    :default :one
    :validate [#{:one :zero} "Unsupported mode"]]
   ["-c" "--config type1|type2|..."
    :desc "config specifies what to do"
    :default :dostuff
    :parse-fn #(if (keyword? %)
                 %
                 (-> % s/lower-case keyword))
    :validate-fn #(contains? configurations %)]
    ["-n" "--name service Name"
     :default (getenv "NAME")]
   [nil "--min number"
    :default 7 :parse-fn #(Integer/parseInt %)]
   [nil "--max number"
    :default 7 :parse-fn #(Integer/parseInt %)]
   [nil "--public true|false" "true or false"
    :default false
    :parse-fn #(Boolean/parseBoolean %)]
   ["-h" "--help"]])

(defn -main [& args]
  (let [{:keys [options arguments errors summary]}
         (parse-opts args
                     command-line-spec)
 ... ) 

这篇关于从字符串解析命令行开关和args的惯用clojure的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆