[plt-scheme] How to change the following code to make it handle nested lists?

From: Geoffrey S. Knauth (geoff at knauth.org)
Date: Tue Nov 25 07:52:21 EST 2008

On Sun, 23 Nov 2008 22:50:00 -0800 (PST), "SamuelXiao"
<foolsmart2005 at gmail.com> said:
> 
> (define (mysum list)
>    (if (null? list)
>        0
>       (+ (car list) (mysum (cdr list)))))
> 
> It can handle the case summing up a list of numbers....however, I want
> to handle case like '(1 (2 3) 4), how can I make it?
> The code can handle (mysum '(1 2 3)) => 6, but when it comes to (mysum
> '(1 (2 3) 4))=>error.  Any help would be appreciated.

In your first example, everything in your list was a number.
In your second example, the list contained a number, a list, and another
number.

The first call sees:  '(1 (2 3) 4)
It adds 1 to (mysum '((2 3) 4))

The second call sees:  '((2 3) 4)
It tries to add '(2 3) to (mysum '(4))
but + was expecting a number, not the list '(2 3)
+ generated the error.

+ got a list because (car '((2 3) 4)) turned out not to be a number.
There could have been a check at that point.
Put another way, do not call + unless every argument is (or will be) a
number.

Do you know about cond?  Have you seen this before?

(cond ((empty? L) ...)
      ((pair? L) ...)
      ((number? L) ...)
      (else ...))

Have you read How to Design Programs (HtDP)?  If so, it would help to
know where you are in the book, because then it is clear what you have
seen so far.  If not, reading HtDP teaches you how to handle situations
like this and many others, so that instinctively you just do the right
thing.  It is online at:  http://www.htdp.org/

-- 
Geoffrey S. Knauth | http://knauth.org/gsk




Posted on the users mailing list.