Deutsch   English   Français   Italiano  
<v5drsj$1f2vg$1@dont-email.me>

View for Bookmarking (what is this?)
Look up another Usenet article

Path: ...!npeer.as286.net!npeer-ng0.as286.net!3.eu.feeder.erje.net!feeder.erje.net!eternal-september.org!feeder3.eternal-september.org!news.eternal-september.org!.POSTED!not-for-mail
From: "B. Pym" <No_spamming@noWhere_7073.org>
Newsgroups: comp.lang.lisp
Subject: Re: Simple recursive list processing question
Date: Tue, 25 Jun 2024 07:33:41 -0000 (UTC)
Organization: A noiseless patient Spider
Lines: 81
Message-ID: <v5drsj$1f2vg$1@dont-email.me>
MIME-Version: 1.0
Content-Type: text/plain; charset=iso-8859-1
Injection-Date: Tue, 25 Jun 2024 09:33:41 +0200 (CEST)
Injection-Info: dont-email.me; posting-host="f3516bad7bad6e8b4774a100ca8eaa7a";
	logging-data="1543152"; mail-complaints-to="abuse@eternal-september.org";	posting-account="U2FsdGVkX19ooQjEBW+eZF6kc8NrF8Ma"
User-Agent: XanaNews/1.18.1.6
Cancel-Lock: sha1:lkZEb93rPlTjzvB9bdKBViLIZ1s=
Bytes: 3311

> > (defun summit (a-list)
> >   (if (not (null a-list))
> >   (let ((x (car a-list)))
> >     (if (null x)
> >       (summit (cdr a-list))
> >       (+ x (summit (cdr a-list)))))))
> >
> >
> > Now it doesn't enter infinite loop, however it doesn't work even
> > for the lists that doesn't contain any nil elements:
> >
> > CL-USER> (summit (list 1 2))
> >
> > And the SBCL debugger complains:
> >
> > Argument Y is not a NUMBER: NIL
> >    [Condition of type SIMPLE-TYPE-ERROR]
> >
> > It seems like I'm trying to do addition using some number
> > and something that is not a number (a nil?).
> >
> > I just couldn't find how to correct it? Can somebody enlighten me?
> >
> Your second post shows that you've solved the problem, so maybe you've
> already figured this out. But notice in your solution above that the
> outer IF does not supply an explicit "else" value. The default is for IF
> to return NIL when the test fails and no "else" clause is provided. This
> is what happens when your first version reaches the end of the list:
> (summit (list 1 2))
> 
> 1. Trace: (SUMMIT '(1 2))
> 2. Trace: (SUMMIT '(2))
> 3. Trace: (SUMMIT 'NIL)
> 3. Trace: SUMMIT ==> NIL
> *** - argument to + should be a number: NIL
> 
> The 2nd call to SUMMIT is waiting to add 2 to the result of the 3rd
> call, which returns NIL by default.
> 
> In case you're interested, here are a few ways to solve Graham's problem:
> ;;;
> ;;;    Ex. 9
> ;;;
> (defun summit-1 (l)
>    (apply #'+ (remove nil l)))
> 
> (defun summit-2 (l)
>    (reduce #'+ (remove nil l)))
> 
> (defun summit-3 (l)
>    (if (endp l)
>        0
>        (let ((x (first l)))
>          (if (null x)
>              (summit-3 (rest l))
>              (+ x (summit-3 (rest l)))) )))
> 
> (defun summit-4 (l)
>    (cond ((endp l) 0)
>          ((null (first l)) (summit-4 (rest l)))
>          (t (+ (first l) (summit-4 (rest l)))) ))
> 
> (defun summit-5 (l)
>    (loop for elt in l
>          when elt
>          sum elt))
> 
> SUMMIT-3 is essentially the same as your second version. The last two
> are not really fair since Graham doesn't introduce COND in chapter 2,
> and he is allergic to LOOP.

Scheme:

(define (summit lst)
  (do ((lst lst (cdr lst))
       (sum 0 (+ sum (or (car lst) 0))))
    ((null? lst)  sum)))

(summit '(1 #f #f 3 #f 5 7 9))
  ===>
25