Что делают символы Clojure при использовании в качестве функций?
При попытке решить проблему 4Clojure "" Универсальный вычислительный движок", включающий переоценку оценки, я случайно позвонил так:
(apply '/ '(16 8))
а не предполагаемый:
(apply / '(16 8))
У этого был запутанный побочный эффект возвращения 8
, который заставлял меня думать, что я испортил свою математику.
Я позже понял свою ошибку после некоторой отладки - я не смог оценить символ /
, прежде чем пытаться ее вызвать, и понял, что clojure.lang.Symbol
должен реализовать clojure.lang.IFn
. Но что делает эта реализация? Все, что я могу сделать, это вернуть nil
с одним аргументом или вторым аргументом, если он указан.
Ответы
Ответ 1
Символы видят себя на карте, как и ключевые слова. См. Реализация символа:
…
122 public Object invoke(Object obj) {
123 return RT.get(obj, this);
124 }
125
126 public Object invoke(Object obj, Object notFound) {
127 return RT.get(obj, this, notFound);
128 }
…
(RT
clojure.lang.RT
, который делает почти все. "RunTime"?)
В приведенном примере поиск не работает (поскольку 16 не является картой), и поэтому возвращается значение notFound
(8).