Lisp HUG Maillist Archive

floating point code without consing?

Hi,

Over the weekend I have been working on some numeric code in lisp, and
(having got the stuff working) have been trying to optimise it. One of the
core functions is a routine to calculate matrix products. I have done all I
can to eliminate the consing which is going on in this function and
was really hoping someone could point out something else I could do to improve
matters. 

(defun matrix-product (m1 m2 m3)
  (declare (type (simple-array single-float (* *)) m1 m2 m3))
  (let ((rows (- (array-dimension m1 0) 1))
        (cols (- (array-dimension m2 1) 1))
        (conf (- (array-dimension m1 1) 1)))
    (declare (type fixnum rows cols conf))
    (loop for i from 0 to cols
          do
          (loop for j from 0 to cols
                do
                (setf (aref m3 i j)
                      (loop for alpha from 0 to conf
                            sum (* (aref m1 i alpha) (aref m2 alpha j))))))
    m3))


(defparameter a0
    (make-array (list 10 10) :element-type 'short-float :initial-element 1.0))


(defparameter b0 
    (make-array (list 10 10) :element-type 'short-float :initial-element 2.0))


(defparameter  c0 
    (make-array (list 10 10) :element-type 'short-float))


On LispWorks 4.2 for Linux (compiling with default settings), I get:

CL-USER 11 > (time (matrix-product a0 b0 c0))
Timing the evaluation of (MATRIX-PRODUCT A0 B0 C0)

user time    =      0.000
system time  =      0.000
Elapsed time =   0:00:00
Allocation   = 62400 bytes standard / 0 bytes fixlen
0 Page faults

Thanks,

Barry Wilkes.

-- 
If in the last few years you haven't discarded a major opinion or  
acquired a new one, check your pulse.  You may be dead.

-- Gelett Burgess (1866-1951)


Re: floating point code without consing?

Barry Wilkes <bew@bcs.org.uk> writes:
....
<snip>

>     (loop for i from 0 to cols
>           do
>           (loop for j from 0 to cols
>                 do
>                 (setf (aref m3 i j)
>                       (loop for alpha from 0 to conf
>                             sum (* (aref m1 i alpha) (aref m2 alpha j))))))
>     m3))
> 

Before anyone points it out - the variable i in the first line should of
course be rows, not cols. That's what happens when you type in code rather
than copying it :) 

Barry.

-- 
If in the last few years you haven't discarded a major opinion or  
acquired a new one, check your pulse.  You may be dead.

-- Gelett Burgess (1866-1951)


Re: floating point code without consing?

|
| (defun matrix-product (m1 m2 m3)
|   (declare (type (simple-array single-float (* *)) m1 m2 m3))
|   (let ((rows (- (array-dimension m1 0) 1))
|         (cols (- (array-dimension m2 1) 1))
|         (conf (- (array-dimension m1 1) 1)))
|     (declare (type fixnum rows cols conf))
|     (loop for i from 0 to cols
|           do
|           (loop for j from 0 to cols
|                 do
|                 (setf (aref m3 i j)
|                       (loop for alpha from 0 to conf
|                             sum (* (aref m1 i alpha) (aref m2 alpha j))
                              into acc single-float finally (return acc)
;;<<<<<<<
                              ))))
|     m3))
|

Adding the marked line removed the consing using CMUCL, but LWW 4.2 doesn't
like the SINGLE-FLOAT type declaration here (or double-float). Seems like a loop
macro bug. You could also put a type declaration after the loop indexs
 (loop for j fixnum below cols ... )
which might help speed things up.

Paul



Updated at: 2020-12-10 09:02 UTC