You are not logged in.
Pages: 1
I have managed to avoid learning Lisp since I wrote my first program some 40 years ago. Despite actually having spent some time with McCarthy and having visited the Symbolics plant in Chatsworth, I just never had the desire to learning anything not evolved from Algol or Fortran. I have decided to fill that void in my experience and have been playing with Common Lisp. Emphasis on play. Also, this may be an academic exercise, but this is not a homework assignment.
I put together a function that performs a modified sieve of Eratosthenes that does work. I realize that this is an example of where iteration would provide a huge speed advantage over mapping, but that was not the point of writing this way.
Here is the code
(defun sieve (n)
(let ((primes (list)))
(do ((i 2 (1+ i)))
((> i n))
(if (not
(find 0 (mapcar (lambda (x) (mod i x)) primes)))
(setf primes (append primes (list i)))))
primes))
(print (sieve 100000))
This runs in about 3 seconds in sbcl and prints all the primes less than 100k. clisp takes about 8 seconds. I wanted to build a vector of primes, and then provide a map function to divide a scalar (which happens to be next number to be tested as to whether it is prime) by the vector of known primes to return a new vector of the modulo values. If any of the modulo values are zero, it is not prime. If it is prime, I wanted to add that prime to the vector of primes and continue. I had no trouble using make-array to create an :adjustable collection, but then I ran into a road block:
I could not figure out how to create a map that would allow me to act on a scalar by a vector and return a vector. To work around this, I re-wrote the code to use lists and to use mapcar. As I said, it works, but I believe the setf to store the list each time is highly inefficient. (The fact that I am doing a lot of unnecessary division because I am using mapping functions notwithstanding). Every mapping function for arrays I could find required that the inputs be vectors and the output a single vector the size of the smallest input vector.
So, the real question is, is there an intrinsic way to create a map so that each element of a vector can be passed, along with a scalar to a function that produces an output vector the size of the input vector?
Last edited by ewaller (2014-11-13 02:19:19)
Nothing is too wonderful to be true, if it be consistent with the laws of nature -- Michael Faraday
Sometimes it is the people no one can imagine anything of who do the things no one can imagine. -- Alan Turing
---
How to Ask Questions the Smart Way
Offline
I found it
The function is map-vec
— Function: map-vec f v
Map the Lisp function f over the Calc vector v. For example, ‘(map-vec 'math-floor v)’ returns a vector of the floored components of vector v.
Nothing is too wonderful to be true, if it be consistent with the laws of nature -- Michael Faraday
Sometimes it is the people no one can imagine anything of who do the things no one can imagine. -- Alan Turing
---
How to Ask Questions the Smart Way
Offline
Pages: 1