Manvi
Manvi

Reputation: 1156

Need help to understand LISP

I am trying to write my own maximum function (with 2 elements in list at present) but getting error while executing simple function as:

(defun max_for_vararg (list)
    (if (null list)
        (nil))
    (if (> (car list) (cdr list))
        (car list)
        (cdr list)))

Error as:

? (max_for_vararg '(2 4))
> Error: The value (4) is not of the expected type REAL.
> While executing: CCL::>-2, in process listener(1).
> Type :POP to abort, :R for a list of available restarts.

I appreciate if someone can help me understand it. Error seems confusing to me as similar function like below is running fine but not returning max value.

(defun max_for_vararg (list)
    (if (null list)
        (nil))
    (if (> (car list))
        (car list)
        (cdr list)))

Upvotes: 0

Views: 77

Answers (2)

Sylwester
Sylwester

Reputation: 48745

There are several errors in you code. I'll give you some pointers on how to improve it.

You try to call a function named nil. The first if has a consequence that does (nil), thus call nil as if it is a defined function. nil in other positions is the empty list so this might be an error unless you have made a function called nil.

The first if is dead code As long as the result of the first if does not throw you into the debugger, the second if will run. Thus when the first if is fixed it will be redundant code. You really should try to have both a consequence and an alternative even though the standard doesn't require it.

(if test-1                      ; predicate
    test-1-true-expression      ; consequent
    test-1-false-expression)    ; alternative

The second if should of course be one of those expressions and not something that happens unconditional to the first.

In the updated code > needs at least two arguments to be useful. You can think of > as a function that tests if all the arguments are in descending order. (> 4) is T since all arguments are in descending order. If you find car, cadr and caddr cryptic you may want to try the aliases first, second, third instead. eg

(> (first list) (second list))  ; is first element greater than second element?

Upvotes: 1

Ophirr33
Ophirr33

Reputation: 185

Use cadr instead of cdr. Cdr gets you the rest of the list, which is a single element list. Thus, you have to call car on that list (car (cdr list)). Since this is a common thing to want to do, they made cadr a function that evaluates out to that.

Upvotes: 2

Related Questions