Ответ 1
Прежде всего, предел применяется только к требуемым позиционным аргументам; вы всегда можете использовать случай переменной arity (& more-args
в сигнатуре функции), чтобы обрабатывать столько аргументов, сколько хотите:
(defn foo [& args]
(count args))
(foo 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25)
;; returns 25
На самом деле, на первый взгляд, & args
скорее всего будет правильным решением вашей проблемы. (Например, вы сможете сопоставить функцию над вашими входными узлами, собранными в последовательность, loop
/recur
по указанной последовательности и т.д. - имеет тенденцию иметь большее значение с большим количеством похожих элементов, чем назначать отдельные имена к каждому из них.
(Обратите внимание, что я не претендую на то, чтобы узнать природу конкретного DSL, который вы переписываете в Clojure, или о тех проблемах, с которыми имеете дело, просто предлагая точки, которые могут вас заинтересовать. у вас очень забавная ситуация, когда это, похоже, не применимо, возможно, вы можете предоставить более подробную информацию, и мы увидим, может ли кто-то здесь предложить полезные советы для работы с ним в Clojure.)
Для полноты вы можете добавить бит & args
к функции, которая принимает первые 19 аргументов в качестве необходимых позиционных аргументов:
(defn bar [a1 a2 a3 a4 a5 a6 a7 a8 a9 a10 a11 a12 a13 a14 a15 a16 a17 a18 a19 & as]
(+ 19 (count as)))
(bar 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25)
;; returns 25
Обратите внимание, что если вы укажете 20 позиционных аргументов и &
arg, то, возможно, произойдет странность.
Что касается обоснования, я полагаю, что это связано с тем, что JVM может очень эффективно отправлять метод по arity, поэтому класс clojure.lang.Fn
имеет метод invoke
, перегруженный для явлений до 20. я "Не совсем уверен, может ли он подняться выше, но я полагаю, что это не то, что люди требуют этого часто... Я имею в виду, что я, конечно, нахожу API, определяющий более 20 позиционных аргументов функции, немного подозрительной.