; What (apply f L) really does? If you only want to know what it
; does, and not how I concluded that, jump to the end of the post.
; But, is there any doubt what apply really does? It applies
; functions or macros on list. Here it is:
(println (apply + (list 1 2 3 4 5)))
; Result will be 15. What else? Well, there is the reason. One of
; the characteristics of Lisp is that some values evaluate to
; themselves - because of that we can sometimes write simpler
; expressions. On the other side, because of that, we do not have
; to face with errors, so we can successefully use some concepts,
; without really understanding it. At least, it holds to me. So,
; I have to write some tests to understand what really happens,
; ie. if + and 1, 2 ... are evaluated - and if they are, how
; many times!. I'll start with following.
(println (apply '+ (list 1 2 3 4 5)))
; Ha - it works. Quoted + doesn't harm! That means that not actually
; '+ is applied, but evaluated '+. If I defined some function f
(set 'f (lambda()(- (last $args) (first $args))))
; I can use apply in both of these forms:
(println (apply 'f (list 1 2 3 4 5)))
(println (apply f (list 1 2 3 4 5)))
; Both of these work and give same result - 4. Interesting, isn't
; it? Now, I'll try to quote those 's in the list:
(println (apply '+ (list '1 '2 '3 '4 '5)))
; It works. So, one might think that evaluated '+ is applied on
; evaluated elements of the list. But it is premature conclusion
; since list as operation itself will remove those quotes. So, we
; can test this one:
(println (apply '+ (list ''1 ''2 ''3 ''4 ''5)))
; Result is - ERR: value expected in function + : ''1
; OK; it would be too much. But look at that error: it appears
; that + got ''1 as argument! Not just '+, but ''+ - like one quote
; is not stripped during evaluation of (list ''1 ''2 ''3 ''4 ''5).
; It cannot be! We'll make another test to confirm our suspects!
; I'll replace ' with quote to catch interpreter "in act."
(println (apply '+ (list (quote (quote 1)) (quote (quote 2)))))
; ERR: value expected in function + : '(quote 1)
; Here you are! That extra ' is added by interpreter.
; Now we have all we need!
; let's say that
; exprL is expression that evaluate to list,
; that if printed looks like
; (value1 value2 ... valuen)
; exprf is expression that evaluates to anything
(apply exprf exprL)
; is equivalent to
((eval exprf) 'value1 'value2 ... 'valuen))
; For example
(apply * (list 1 2 3 4 5))
; is really equivalent to
((eval *) '1 '2 '3 '4 '5)
; You didn't seen that eval and those quotes, did you? Maybe you
; did, but I did not.