home *** CD-ROM | disk | FTP | other *** search
/ NetNews Usenet Archive 1992 #20 / NN_1992_20.iso / spool / comp / lang / lisp / 2429 < prev    next >
Encoding:
Text File  |  1992-09-14  |  2.2 KB  |  60 lines

  1. Path: sparky!uunet!sun-barr!ames!think.com!barmar
  2. From: barmar@think.com (Barry Margolin)
  3. Newsgroups: comp.lang.lisp
  4. Subject: Re: copy-array?
  5. Date: 14 Sep 1992 23:01:51 GMT
  6. Organization: Thinking Machines Corporation, Cambridge MA, USA
  7. Lines: 48
  8. Message-ID: <1935kvINNi3f@early-bird.think.com>
  9. References: <9209142212.AA24213@brownie.cs.wisc.edu>
  10. NNTP-Posting-Host: telecaster.think.com
  11.  
  12. In article <9209142212.AA24213@brownie.cs.wisc.edu> so@CS.WISC.EDU (Bryan S. So) writes:
  13. >This is almost the first time I seriously use arrays
  14. >in Common Lisp.  Now, how come there is no intrinsic
  15. >function to make a copy of an array?
  16.  
  17. There was a proposal in X3J13 to extend some of the sequence functions to
  18. work on multidimensional arrays, but it was voted down.  That would have
  19. enabled COPY-SEQ to do what you want.
  20.  
  21. It's kind of a shame that a multidimensional array can't be used as the
  22. :INITIAL-CONTENTS argument for MAKE-ARRAY, even when it matches the
  23. dimensionality of the array being built.  Then you could do:
  24.  
  25. (make-array ... :initial-contents old-array)
  26.  
  27. >The only algorithm I have is to make a new array then
  28. >assign the elements one by one.  Is there an easier/
  29. >more efficient method to do this?
  30.  
  31. You can do it using displaced arrays and MAP-INTO:
  32.  
  33. (defun copy-array (old-array)
  34.   (let* ((type (array-element-type old-array))
  35.      (size (array-total-size old-array))
  36.      (new-array (make-array (array-dimensions old-array)
  37.             :element-type type))
  38.      (old-vector (make-array size :element-type type :displaced-to old-array))
  39.      (new-vector (make-array size :element-type type :displaced-to new-array)))
  40.     (copy-into new-vector #'identity old-vector)
  41.     new-array))
  42.  
  43. A possibly more efficient way to implement this is:
  44.  
  45. (defun copy-array (old-array)
  46.   (let* ((type (array-element-type old-array))
  47.      (size (array-total-size old-array))
  48.      (old-vector (make-array size :element-type type :displaced-to old-array))
  49.      (new-vector (copy-seq old-vector)))
  50.     (make-array (array-dimensions old-array) :element-type type
  51.     :displaced-to new-vector)))
  52.  
  53. However, this has the misfeature that the resulting array is likely to be
  54. more expensive to access, because it's displaced.
  55. -- 
  56. Barry Margolin
  57. System Manager, Thinking Machines Corp.
  58.  
  59. barmar@think.com          {uunet,harvard}!think!barmar
  60.