Re: memory usage issue for double-float operations
Michał "phoe" Herda via Sbcl-help <[email protected]>
| Newsgroups | gmane.lisp.steel-bank.general |
|---|---|
| Message-ID | <[email protected]> |
Converting a double float to a function argument requires boxing, which allocates memory. If the function is inlined, there are no arguments to pass, so there can be no consing. On 26.09.2024 01:55, Matt Kaufmann wrote: > Thanks so much! > > I see that suitable THE declarations also avoid consing. But > inserting a function call can cause consing, whether using THE or your > declaim form, as illustrated below. I'd be interested in any insights > about why that function call causes consing. > > (declaim (optimize (compilation-speed 0) (debug 0) (speed 3) (space 0) > (safety 0))) > > ; Optional: > ; (declaim (type (simple-array double-float (5000)) *ar*)) > > (defvar *ar* (make-array '(5000) > :element-type 'double-float > :initial-element 0.0d0)) > > (loop with i of-type (integer 0 *) = 0 do > (cond ((>= i 5000) > (return)) > (t (progn (setf (aref *ar* i) > (float i 0.0d0)) > (setq i (1+ i)))))) > > (defun foo (ar) > (loop with i = 0 do > (cond > ((>= i 4999) ; <-- for i from 0 to 4999 ... > (return)) > (t (setf (aref (the (simple-array double-float (*)) ar) > i) > (the double-float > (+ 1.0d0 > (the double-float > (aref (the (simple-array double-float *) ar) > i))))) > (setq i (1+ i)))))) > > (time (foo *ar*)) ; 0 bytes consed > > ; Optional: > (declaim (inline my-update)) > > (defun my-update (ar i v) > (declare (type (simple-array double-float (*)) ar) > (type double-float v)) > (setf (aref (the (simple-array double-float (*)) ar) > i) > v)) > > (defun foo2 (ar) > (loop with i = 0 do > (cond > ((>= i 4999) ; <-- for i from 0 to 4999 ... > (return)) > (t (my-update ar > i > (the double-float > (+ 1.0d0 > (the double-float > (aref (the (simple-array double-float *) > ar) > i))))) > (setq i (1+ i)))))) > > (time (foo2 *ar*)) ; 65,536 bytes consed if not inlined, 0 otherwise > > Thanks, > Matt > Michał "phoe" Herda <[email protected]> writes: > >> (declaim (type (simple-array double-float (5000)) *ar*)) >> >> On 25.09.2024 21:44, Matt Kaufmann wrote: >>> Hi, >>> >>> Is there a way to modify the example below so that the final form does >>> not allocate memory in SBCL? (To be fair, I tried several other Lisps >>> as well, and all of them allocated memory.) >>> >>> (declaim (optimize (compilation-speed 0) (debug 0) (speed 3) (space 0) >>> (safety 0))) >>> >>> (defvar *ar* (make-array '(5000) >>> :element-type 'double-float >>> :initial-element 0.0d0)) >>> >>> (loop with i of-type (integer 0 *) = 0 do >>> (cond ((>= i 5000) >>> (return)) >>> (t (progn (setf (aref *ar* i) >>> (float i 0.0d0)) >>> (setq i (1+ i)))))) >>> >>> (defun foo () >>> (loop with i of-type fixnum = 0 do >>> (cond >>> ((>= i 4999) ; <-- for i from 0 to 4999 ... >>> (return)) >>> (t (setf (aref *ar* i) >>> (the double-float >>> (+ 1.0d0 >>> (the double-float (aref *ar* i))))) >>> (setq i (the fixnum (1+ i))))))) >>> >>> (time (foo)) >>> >>> Thanks, >>> Matt >>> >>> >>> _______________________________________________ >>> Sbcl-help mailing list >>> [email protected] >>> https://lists.sourceforge.net/lists/listinfo/sbcl-help _______________________________________________ Sbcl-help mailing list [email protected] https://lists.sourceforge.net/lists/listinfo/sbcl-help