On 19/06/2015 21:24, Luke Miles wrote:
Say I have a list ls and I want to produce a list of
lists where the i'th list has the i'th element of ls tripled,
but all other elements are the same.

e.g. '(3 5 7) => '((9 5 7) (3 15 7) (3 5 21))

What is a fast way to do this?


I could do a loop with appending.
(define (map-once f ls)
   (let M ([sooner null] [later ls])
     (if (null? later) null
       (cons (append sooner (list (f (car later))) (cdr later))
             (M (append sooner (list (car later))) (cdr later))))))

-> (map-once sqr '(4 5 6))
'((16 5 6) (4 25 6) (4 5 36))

Unfortunately, this is very slow & messy.
I have to do 2 big appends for every element is the return list.


Here is a cleaner-looking, but still slow way:
(define (list-set ls i new-val)
   (let-values ([(sooner later) (split-at ls i)])
     (append sooner (list new-val) (cdr later))))

(define (map-once f ls)
   (for/list ([i (in-naturals)]
              [elm (in-list ls)])
     (list-set ls i (f elm))))


I'm thinking a good implementation might use continuations somehow?


I would start out with i lists in a vector of length i and construct them according to their index and the index of the current element in the source list. The "key expressions" would be
(make-vector i '())
(when (= vector-idx list-idx) (f ...
(vector->list ...

This way you should be able recurse or iterate with an inner definition. Is it better to use single linked lists or double linked lists as the internal data graph of the text edit <buffer>? I think with 64bit pointers and up to 90.000 lines as a sane soft maximum single linked lists with a register holding the number of the current line on screen would perform better and are generally easier to handle. Oops, that was not meant to end up here ...

--
You received this message because you are subscribed to the Google Groups "Racket 
Users" group.
To unsubscribe from this group and stop receiving emails from it, send an email 
to racket-users+unsubscr...@googlegroups.com.
For more options, visit https://groups.google.com/d/optout.

Reply via email to