[英]How to use command line arguments in Clojure?
我正在研究我的第一个 Clojure 程序。 我剩下要做的一件事是让我的程序接受命令行参数。 args 的数量可以变化(但至少需要一个),然后每个命令行 arg 需要作为参数提供给我的main
的函数,一次一个。 我一直在网上阅读,似乎clojure/tools.cli
是这样做的方法,(可能使用parse-opts
?)。 但我无法弄清楚我的生活。 没有验证,确实需要进行验证——用户提供的任何内容都是有效的。 (唯一需要检查的是至少提供了一个参数)。 关于如何解决这个问题的任何建议?
我遇到的所有示例看起来都非常复杂,而且很容易让我无法理解。
我正在尝试做的一个简单示例是在用户提供任意数量的命令行参数之后,然后让 clojure 在终端的新行中打印每个字符串。
我使用 leiningen 来运行我的程序。
简单的方法是使用clojure.core/*command-line-args*
:
(doseq [arg *command-line-args*]
(println (str "Read an argument: " arg)))
由于您的整个问题似乎归结为:
我正在尝试做的一个简单示例是在用户提供任意数量的命令行参数之后,然后让 clojure 在终端的新行中打印每个字符串。
我会回答那个。 这可以相当简洁地完成:
(defn -main [& args] ; & creates a list of var-args
(if (seq args)
; Foreach arg, print the arg...
(doseq [arg args]
(println arg))
; Handle failure however here
(throw (Exception. "Must have at least one argument!"))))
请注意,除非您绝对想在传递 0 个参数时彻底失败,否则您可以跳过seq
检查。 如果args
为空,则doseq
将不会运行,因为没有任何要迭代的内容。
您还可以将整个doseq
替换为:
(mapv println args)
但这可以说是对mapv
的滥用。
Clojure Spec可以做很多事情,解析和验证命令行参数就是其中之一。 下面是一个例子:
(ns cmdargs.core
(:require [clojure.spec.alpha :as spec]))
;; Specification of a single argument.
;; For example, replace `any?` by `number?`
;; if your program only accepts numeric args.
(spec/def ::arg any?)
(spec/def ::args (spec/+ ::arg))
(defn my-fun [& args]
(doseq [arg args]
(println "Got arg: " arg)))
(defn -main [& args]
(let [parsed-args (spec/conform ::args args)]
(if (= ::spec/invalid parsed-args)
(do (println "Bad commandline arguments")
(spec/explain ::args args))
(apply my-fun parsed-args))))
Clojure Spec 从 Clojure 1.9 版开始提供。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.