mapcar or notmapcar

Discussion of Common Lisp
burton
Posts: 10
Joined: Sat Aug 28, 2010 6:05 pm

mapcar or notmapcar

Post by burton » Tue Aug 31, 2010 8:44 pm

hi,im trying to get the following:
the input is a list of numbers (integers eg. (1 2 3 4) (5 6 7 8)) and the expected output is ((1*5)+(2*6)+(3*7)+(4*8))/(the sum of the second list).
is there a non-recursive way of solving it?


> (mapcar #'list '(1 2 3 4) '(5 6 7 8))
((1 5) (2 6) (3 7)(4 8))

i was thinking about mapcar, which would do the trick with a little tweaking, but how?
any ideas?
thanks

Duke
Posts: 38
Joined: Sat Oct 17, 2009 10:40 pm
Contact:

Re: mapcar or notmapcar

Post by Duke » Tue Aug 31, 2010 8:59 pm

Yeah, you want MAPCAR. What you do not want is #'LIST. ;)
You'll also need one or two REDUCEs (or APPLYs) to get the sums.
"If you want to improve, be content to be thought foolish and stupid." -Epictetus

Tom
Posts: 22
Joined: Sat Jun 28, 2008 12:52 pm
Location: Wichita, KS
Contact:

Re: mapcar or notmapcar

Post by Tom » Tue Aug 31, 2010 9:56 pm

Using MAPCAR and REDUCE is fine. As an alternative approach, you could LOOP.

Code: Select all

(defun notmapcar (list1 list2)
  "(list1 x list2) / Sum(list2)"
  (if (= (length list1) (length list2))
      (loop for val1 in list1
            and val2 in list2
            sum (* val1 val2) into num
            sum val2 into den
            finally (return (/ num den)))
      (error "The lists are not equal in length.")))
There are many ways to iterate in Common Lisp.

Edit: I was about to close down lisp when I just couldn't resist write a version with MAPCAR. It's not totally functional, but it only traverses the lists once.

Code: Select all

(defun tomapcar (list1 list2)
  "(list1 x list2) / Sum(list2)"
  (let ((num 0)
        (den 0))
    (mapcar (lambda (n1 n2)
              (incf num (* n1 n2))
              (incf den n2))
            list1
            list2)
    (/ num den)))

~ Tom

Tordmor
Posts: 1
Joined: Sat Aug 21, 2010 1:42 am

Re: mapcar or notmapcar

Post by Tordmor » Wed Sep 01, 2010 4:55 am

Duke wrote:Yeah, you want MAPCAR. What you do not want is #'LIST. ;)
What's wrong with #'list?

gugamilare
Posts: 406
Joined: Sat Mar 07, 2009 6:17 pm
Location: Brazil
Contact:

Re: mapcar or notmapcar

Post by gugamilare » Wed Sep 01, 2010 5:03 am

Tordmor wrote:
Duke wrote:Yeah, you want MAPCAR. What you do not want is #'LIST. ;)
What's wrong with #'list?
It does not do what he wants ;)

Warren Wilkinson
Posts: 117
Joined: Tue Aug 10, 2010 11:24 pm
Location: Calgary, Alberta
Contact:

Re: mapcar or notmapcar

Post by Warren Wilkinson » Wed Sep 01, 2010 12:55 pm

Code: Select all

(defun operation (f-list s-list)
  (/ (reduce #'+ (mapcar #'* f-list s-list)) (reduce #'+ s-list)))

(operation '(1 2 3 4) '(5 6 7 8))  ;; gives 35/13

Need an online wiki database? My Lisp startup http://www.formlis.com combines a wiki with forms and reports.

burton
Posts: 10
Joined: Sat Aug 28, 2010 6:05 pm

Re: mapcar or notmapcar

Post by burton » Wed Sep 01, 2010 4:39 pm

Warren, is there a way to get decimals as a result instead of a fraction?

gugamilare
Posts: 406
Joined: Sat Mar 07, 2009 6:17 pm
Location: Brazil
Contact:

Re: mapcar or notmapcar

Post by gugamilare » Wed Sep 01, 2010 7:01 pm

You can use the function FLOAT to convert a number (rational or integer) into a float.

Warren Wilkinson
Posts: 117
Joined: Tue Aug 10, 2010 11:24 pm
Location: Calgary, Alberta
Contact:

Re: mapcar or notmapcar

Post by Warren Wilkinson » Wed Sep 01, 2010 11:26 pm

Why would you want floats/decimal numbers? You could opt to use the more accurate rational numbers throughout your code and then use format's "~f" operator to print the result as a floating point number.
Need an online wiki database? My Lisp startup http://www.formlis.com combines a wiki with forms and reports.

findinglisp
Posts: 447
Joined: Sat Jun 28, 2008 7:49 am
Location: Austin, TX
Contact:

Re: mapcar or notmapcar

Post by findinglisp » Sun Sep 05, 2010 6:08 am

Warren Wilkinson wrote:Why would you want floats/decimal numbers?
Depends on the code. Floats will generally be handled with greater performance by the hardware; rationals are Lisp-only concepts that have to be manipulated in software, with many extra steps. But as you point out, rationals will keep better precision through a many-step calculation.
Cheers, Dave
Slowly but surely the world is finding Lisp. http://www.findinglisp.com/blog/

Post Reply