From: Wisdo
Subject: Newbie Question:  how to use   Assoc  and pair together.
Date: 
Message-ID: <edo4md$dm7$1@news.yaako.com>
Hi ,

I'm a newbie for Lisp,  for 2 days' learning,
I find it's interesting and powerfull.

I follow the example of  "roots_of_lisp".

and write

(defun pair. (x y)
        (cond ((and. (null. x) (null. y)) '())
                ((and. (not. (atom x)) (not. (atom y)))
                        (cons (list (car x) (car y))
                                (pair. (cdr x) (cdr y))))))

(defun assoc. (x y)
        (cond ((eq (x (caar y))) (cadar y))
                ('t (assoc. x (cdr y)))))

but when i test assoc. function, i get error.

[1]> (pair. '(a b) '(c d))
((A C) (B D))
[2]> (assoc. 'a (pair. '(a b) '(c d))
)

*** - EVAL: undefined function X
The following restarts are available:
USE-VALUE      :R1      You may input a value to be used instead of
(FDEFINITION 'X).
RETRY          :R2      Retry
STORE-VALUE    :R3      You may input a new value for (FDEFINITION 'X).
ABORT          :R4      ABORT

what's the problem above ? and how to test assoc in right way.

I use  GNU CLISP 2.39 (2006-07-16) (built 3366326912) (memory 3366327837);

Thanks in advance.
Wisdo

From: D Herring
Subject: Re: Newbie Question:  how to use   Assoc  and pair together.
Date: 
Message-ID: <z5adnTUSHPUKAWLZnZ2dnUVZ_qGdnZ2d@comcast.com>
Your error is coming from this definition:
> (defun assoc. (x y)
>   (cond
>     ((eq (x (caar y))) (cadar y))
>     ('t (assoc. x (cdr y)))))

Specifically, the x in "(eq (x (caar y)) ...".
Since the first symbol after a '(' is (almost) always treated as a
function, you are getting the error:
> [2]> (assoc. 'a (pair. '(a b) '(c d)) )
> 
> *** - EVAL: undefined function X

Lisp is expecting a function named x, ignoring the variable x='a,
and complaining that you don't have a function named x.  (One
{advantage,pitfall} of Lisp is that each symbol can have multiple
values -- one as a function, one as a variable, and others that the
user can define.)

Solution: Remove the extra parentheses surrounding (x (caar y)).
Also, don't quote the 't'; the truth value is a bare _t_, not _'t_.

For a slight improvement in clarity, you could replace the
(cond) with an (if), since there are only two cases.

Later,
Daniel
From: D Herring
Subject: Re: Newbie Question:  how to use   Assoc  and pair together.
Date: 
Message-ID: <z5adnTQSHPUQAGLZnZ2dnUVZ_qGdnZ2d@comcast.com>
D Herring wrote:
> Your error is coming from this definition:
>> (defun assoc. (x y)
>>   (cond
>>     ((eq (x (caar y))) (cadar y))
>>     ('t (assoc. x (cdr y)))))

And you probably want (eql) or (equal) instead of (eq).
From: Wisdo
Subject: Re: Newbie Question:  how to use   Assoc  and pair together.
Date: 
Message-ID: <edo84n$gp6$1@news.yaako.com>
D Herring �:
> D Herring wrote:
>> Your error is coming from this definition:
>>> (defun assoc. (x y)
>>>   (cond
>>>     ((eq (x (caar y))) (cadar y))
>>>     ('t (assoc. x (cdr y)))))
> 
> And you probably want (eql) or (equal) instead of (eq).

Thanks Herring,
for your detail words, it's OK now.
From: Jack Unrue
Subject: Re: Newbie Question:  how to use   Assoc  and pair together.
Date: 
Message-ID: <uq5vf21mte783n7ha3vtd97u8d6uftdavn@4ax.com>
On Thu, 07 Sep 2006 11:46:21 +0800, Wisdo <·····@hf.webex.com> wrote:
> 
> (defun assoc. (x y)
>         (cond ((eq (x (caar y))) (cadar y))
>                 ('t (assoc. x (cdr y)))))
> 
> but when i test assoc. function, i get error.
> 
> [1]> (pair. '(a b) '(c d))
> ((A C) (B D))
> [2]> (assoc. 'a (pair. '(a b) '(c d))
> )
> 
> *** - EVAL: undefined function X

Ponder the following questions:

1- where is the symbol X mentioned in the definition
   of ASSOC. ?

2- of those locations, is there a spot where it has to
   evaluate to a function value?

3- to what does X actually evaluate at that location, based
   on how you called ASSOC.  ?

Having thought about that, I then want you to go read an IRC
log, specifically: http://tunes.org/~nef/logs/lisp/06.08.23
and scroll down to the 12:20:02 mark, where you will be able
to read a fantastic tutorial on this subject given by someone
with the nick Riastradh. I highly recommend that you read
it all the way through.

-- 
Jack Unrue
From: Wisdo
Subject: Re: Newbie Question:  how to use   Assoc  and pair together.
Date: 
Message-ID: <edocpk$lhs$1@news.yaako.com>
Jack Unrue wrote:

> Ponder the following questions:
> 
> 1- where is the symbol X mentioned in the definition
>    of ASSOC. ?
> 
> 2- of those locations, is there a spot where it has to
>    evaluate to a function value?
> 
> 3- to what does X actually evaluate at that location, based
>    on how you called ASSOC.  ?
> 
> Having thought about that, I then want you to go read an IRC
> log, specifically: http://tunes.org/~nef/logs/lisp/06.08.23
> and scroll down to the 12:20:02 mark, where you will be able
> to read a fantastic tutorial on this subject given by someone
> with the nick Riastradh. I highly recommend that you read
> it all the way through.
> 

thanks your kind clue�� Jack.

I found the reason. i change it to

(defun assoc. (x y)
        (cond ((eq x (caar y)) (cadar y))
                (t (assoc. x (cdr y)))))
and test it's OK
[1]> (assoc. 'a (pair. '(a b) '(c d)))
C

my unstanding is the first node in any list should be consider as function,
but x isn't function, so  (x ...) will cause problem.


I follow the irc log link,
but it seems i need learn more to understand it. :(

after all, i got one thing
(lambda (x) 5) is macro form and will expand to
(function (lambda (x) 5).
From: Wisdo
Subject: Re: Newbie Question:  how to use   Assoc  and pair together.
Date: 
Message-ID: <edohtb$rc7$1@news.yaako.com>
Jack Unrue wrote:
> On Thu, 07 Sep 2006 11:46:21 +0800, Wisdo <·····@hf.webex.com> wrote:
>> (defun assoc. (x y)
>>         (cond ((eq (x (caar y))) (cadar y))
>>                 ('t (assoc. x (cdr y)))))
>>
>> but when i test assoc. function, i get error.
>>
>> [1]> (pair. '(a b) '(c d))
>> ((A C) (B D))
>> [2]> (assoc. 'a (pair. '(a b) '(c d))
>> )
>>
>> *** - EVAL: undefined function X
> 
> Ponder the following questions:
> 
> 1- where is the symbol X mentioned in the definition
>    of ASSOC. ?
> 
> 2- of those locations, is there a spot where it has to
>    evaluate to a function value?
> 
> 3- to what does X actually evaluate at that location, based
>    on how you called ASSOC.  ?
> 
> Having thought about that, I then want you to go read an IRC
> log, specifically: http://tunes.org/~nef/logs/lisp/06.08.23
> and scroll down to the 12:20:02 mark, where you will be able
> to read a fantastic tutorial on this subject given by someone
> with the nick Riastradh. I highly recommend that you read
> it all the way through.
> 

Hi Jack,

I think i need read again, actually i did,  and  got much this time.

as my unstanding,

if without lambda macro ,

(lambda (x) 5) is actually a function expression.
it's a abstract concept.

but some time we need the actual value object of  function.
it's  (funtion (lambda (x) 5)).

for the (f args)  statement,  f must be a function expression.
so   ((lambda (x) 5) 2) --> 5   is OK
but ((function (lambda (x) 5) 2)  is wrong ,
because (function (lambda (x) 5)) is value expression.

in the same regular,
mapcar need a value object of function as its argument, so

(mapcar (function (lambda (x) 5)) '(1 2 3 4))  -> (5 5 5 5) is OK

but if without  lambda macro
(mapcar (lambda (x) 5) '(1 2 3 4)   is wrong.

I think above is right.


but i have another problems.
i write the make-lambda following Riastradh.

(defun make-lambda (bvl body) (cons 'lambda (cons bvl body)))

i think i return a function expression. i.e.
(make-lambda '(x) 5)  -> i think should be (lambda (x) 5),
but result is (LAMBDA (X) . 5)	  one more dot appear.

as function expression , it should be called directly. as
((lambda (x) 5) 3)  -> 5
((make-lambda '(x) 5) 3)  -> should be 5 , but error occur

could you tell me the reason?

thanks.
Wisdo
From: Pascal Bourguignon
Subject: Re: Newbie Question:  how to use   Assoc  and pair together.
Date: 
Message-ID: <87ac5b4xwn.fsf@thalassa.informatimago.com>
Wisdo <·····@hf.webex.com> writes:
> I think i need read again, actually i did,  and  got much this time.
> as my unstanding,
> if without lambda macro ,
>
> (lambda (x) 5) is actually a function expression.
> it's a abstract concept.

Yes.  The name used in CLHS is lambda expression.

http://www.lispworks.com/documentation/HyperSpec/Body/26_glo_l.htm#lambda_expression


> but some time we need the actual value object of  function.
> it's  (funtion (lambda (x) 5)).

But when you evaluate (lambda (x) 5), you don't need to write
(function ...) (or #') because cl:lambda is a macro that expands to
(function (lambda ...)).

LISP> (quote (lambda (x) (+ 5 x)))
(LAMBDA (X) (+ 5 X))
LISP> (function (lambda (x) (+ 5 x)))
#<FUNCTION :LAMBDA (X) (+ 5 X)>
LISP> (lambda (x) (+ 5 x))
#<FUNCTION :LAMBDA (X) (+ 5 X)>
LISP> (macroexpand-1 '(lambda (x) (+ 5 x)))
#'(LAMBDA (X) (+ 5 X)) ;
T

;; This is actually (FUNCTION (LAMBDA (X) (+ 5 X)))
;; My CL implementation writes #'x instead of (function x) :
LISP> (quote (function relation))
#'RELATION
LISP> (COM.INFORMATIMAGO.COMMON-LISP.CONS-TO-ASCII:PRINT-CONSES
             (macroexpand-1 '(lambda (x) (+ 5 x))))
(FUNCTION  . ((LAMBDA  . ((X  . ()) . ((+  . (5  . (X  . ()))) . ()))) . ()))
#'(LAMBDA (X) (+ 5 X))


> for the (f args)  statement,  f must be a function expression.
> so   ((lambda (x) 5) 2) --> 5   is OK
> but ((function (lambda (x) 5) 2)  is wrong ,
> because (function (lambda (x) 5)) is value expression.

Yes.


> in the same regular,
> mapcar need a value object of function as its argument, so
>
> (mapcar (function (lambda (x) 5)) '(1 2 3 4))  -> (5 5 5 5) is OK
>
> but if without  lambda macro
> (mapcar (lambda (x) 5) '(1 2 3 4)   is wrong.
>
> I think above is right.


(mapcar (lambda (x) 5) '(1 2 3 4)   is wrong because there's a
parenthesis missing.

(mapcar (lambda (x) 5) '(1 2 3 4))  is correct because the lambda macro
expands it to (function (lambda (x) 5)).



> but i have another problems.
> i write the make-lambda following Riastradh.
>
> (defun make-lambda (bvl body) (cons 'lambda (cons bvl body)))
>
> i think i return a function expression. i.e.
> (make-lambda '(x) 5)  -> i think should be (lambda (x) 5),
> but result is (LAMBDA (X) . 5)	  one more dot appear.

Given this definition:

   (defun make-lambda (bvl body) (cons 'lambda (cons bvl body)))

BODY is expected to be a list.  It must be called as:

   (make-lambda '(x) '(5))

If you want to be able to call it with:

   (make-lambda '(x) 5)

then you must define as:

   (defun make-lambda (bvl &rest body) (cons 'lambda (cons bvl body)))

But then if you have several expressions for the body, you'll need to
quote them all:
      
   (make-lambda '(x) '(print 'start) '(print x) '(prog1 5 (print 'done)))


> as function expression , it should be called directly. as
> ((lambda (x) 5) 3)  -> 5
> ((make-lambda '(x) 5) 3)  -> should be 5 , but error occur
>
> could you tell me the reason?

This is because the first item of a form is not evaluated in Common Lisp.
It must be known as a function (or macro or special operator) by the compiler.

   ((lambda (x) (+ 5 x)) 1)  

        here, (lambda (x) (+ 5 x)) is not evaluated, it's directly
        compiled as the function it is by the compiler.


   (mapcar (lambda (x) (+ 5 x)) '(1 2 3))

        here,  (lambda (x) (+ 5 x)) is evaluated, 
        which macroexpands to: (function (lambda (x) (+ 5 x))) 
        and evaluates the the function object (value).

-- 
__Pascal Bourguignon__                     http://www.informatimago.com/
-----BEGIN GEEK CODE BLOCK-----
Version: 3.12
GCS d? s++:++ a+ C+++ UL++++ P--- L+++ E+++ W++ N+++ o-- K- w--- 
O- M++ V PS PE++ Y++ PGP t+ 5+ X++ R !tv b+++ DI++++ D++ 
G e+++ h+ r-- z? 
------END GEEK CODE BLOCK------
From: Jack Unrue
Subject: Re: Newbie Question:  how to use   Assoc  and pair together.
Date: 
Message-ID: <dr80g294c99h9aj74qish3jbk7rmisauud@4ax.com>
On Thu, 07 Sep 2006 15:19:20 +0200, Pascal Bourguignon <···@informatimago.com> wrote:
>
> Wisdo <·····@hf.webex.com> writes:
> 
> > as function expression , it should be called directly. as
> > ((lambda (x) 5) 3)  -> 5
> > ((make-lambda '(x) 5) 3)  -> should be 5 , but error occur
> >
> > could you tell me the reason?
> 
> This is because the first item of a form is not evaluated in Common Lisp.
> It must be known as a function (or macro or special operator) by the compiler.

Right. So the key question that I asked Wisdo to consider
was not correct:

    2- of those locations, is there a spot where it has to
       evaluate to a function value?

because evaluation has nothing to do with it in the context of the original
problem, and this is why the error message is phrased the way it is.

>    ((lambda (x) (+ 5 x)) 1)  
> 
>         here, (lambda (x) (+ 5 x)) is not evaluated, it's directly
>         compiled as the function it is by the compiler.
> 
> 
>    (mapcar (lambda (x) (+ 5 x)) '(1 2 3))
> 
>         here,  (lambda (x) (+ 5 x)) is evaluated, 
>         which macroexpands to: (function (lambda (x) (+ 5 x))) 
>         and evaluates the the function object (value).

-- 
Jack Unrue