2010-04-30 6 views
5

Некоторое время назад этот код работал, но теперь его больше нет. С этим что-то не так?Функция Sum не работает:/

user=> (defn sum [a b] (a + b)) 
#'user/sum 
user=> (sum 3 4) 
java.lang.ClassCastException: java.lang.Integer cannot be cast to clojure.lang.IFn (NO_SOURCE_FILE:0) 
user=> 

Это, вероятно, время, чтобы сделать перерыв :)

ответ

9

Возможно попробовать:

(defn sum [a b] (+ a b)) 

Clojure, являясь членом лисповской семьи, всегда использует префикс обозначения для арифметических выражений.

+0

Да, я забыл. – StackedCrooked

2

Поскольку вы пытаетесь написать такую ​​функцию, интересно, полезно ли указывать, что + является обычной функцией в Clojure, как и в любом другом Lisp. На самом деле, нет специальных «арифметических выражений» в Clojure, просто функциональных приложений, аргументами которых являются числа и операторы которых выполняют арифметические операции.

Фактически, в большинстве Lisps нет специальных «операторов» в смысле выделенных фрагментов синтаксиса, которые необходимо было бы обернуть, чтобы их функциональность была доступна в виде функции. Clojure необычен как Lisp в этом отношении тем, что он явно зависит от его хост-платформы для некоторых довольно простых функций; например возвышение с плавающей точкой доступно в ванильном Clojure в виде метода pow класса java.lang.Math (но см. clojure.contrib.math для некоторых приятных функций для выполнения различных арифметических операций не в clojure.core).

Методы Java должны быть завернуты в Clojure, которые будут использоваться в качестве функций (например, переданы в map и т. Д.), Поэтому они могут использовать операторы на таких языках, как C, Python или сама Java. Тем не менее, они все еще называются с использованием префиксной нотации.

2
  • В clojure.core уже есть функция +, поэтому будьте очень осторожны при ее переопределении, возможно, вам лучше избежать этого.
  • Все буквы, включая Clojure, используют префиксные обозначения. Вы должны вызвать функцию, например (fn-name args). В вашем примере Clojure пытается вызвать Integer как функцию, потому что это первый элемент списка. Целые элементы не реализуют интерфейс IFn, поэтому это объясняет сообщение об ошибке.
  • На самом деле вы можете получить инфиксную нотацию для математических функций, используя функцию. Для этой функции см. Стр. 13 первой главы The Joy Of Clojure, свободно доступной здесь: http://www.manning.com/fogus/Fogus_MEAP_Ch1.pdf.
+0

Несмотря на то, что этот конкретный пример инфикса не внесет его в окончательный проект, я должен отметить, что он был реализован как функция, а не макрос. – fogus

+0

@fogus Отредактировано соответственно. –

Смежные вопросы