;;;; Vector (define (vector-each-impl fn vec veclen) (do ((i 0 (+ i 1))) ((= i veclen)) (fn (vector-ref vec i)))) (define (vector-each fn vec) (vector-each-impl fn vec (vector-length vec))) (define (vector-each-neigh fn vec) (void)) ;;; Asserts that both `invec` and `outvec` are of the same length ;;; `invec` and `outvec` can be the same vector (define (vector-do fn invec outvec len) (do ((i 0 (+ i 1))) ((= i len)) (vector-set! outvec i (fn (vector-ref invec i))))) (define (vector-map fn vec) (let* ((veclen (vector-length vec)) (resv (make-vector veclen))) (vector-do fn vec resv veclen) resv)) ;;; In-place map (define (vector-map! fn vec) (vector-do fn vec vec (vector-length vec))) ;;;; Dynamic vector ;;; Make a dynamic vector (define (make-dynvec len cap) (cons len (make-vector cap))) (define (dynvec-length dvec) (car dvec)) (define (dynvec-cap dvec) (vector-length (cdr dvec))) (define (dynvec-ref dvec i) (vector-ref (cdr dvec) i)) (define (dynvec->vec dvec) (cdr dvec)) (define (dynvec-vec dvec) (cdr dvec)) (define (dynvec-resize! dvec newcap) (let ((nvec (make-vector newcap))) (do ((i 0 (+ i 1))) ((= i 0))))) ;;; Appends elements to a dynamic vector, resizing if needed. (define (dynvec-append! dvec . args) (let ((i (dynvec-length dvec)) (cap (dynvec-cap dvec))) (for-each (lambda (v) (vector-set! (dynvec-vec dvec) i v) (set! i (+ i 1)) (if (= i cap) (dynvec-resize! dvec (* dvec 2)))) args) (set-car! dvec i))) (define (dynvec-each fn dvec) (vector-each-impl fn (dynvec-vec dvec) (dynvec-length dvec))) (define (dynvec-map fn dvec) (let* ((len (dynvec-length dvec)) (resdv (make-dynvec len len))) (vector-do fn (dynvec-vec dvec) (dynvec-vec resdv) len) resdv)) (define (dynvec-map! fn dvec) (let ((vec (dynvec-ref dvec))) (vector-do fn vec vec (dynvec-length dvec)))) (define (dynvec-to-list-rec dvec lst i) (if (< i 0) lst (dynvec-to-list-rec dvec (cons (dynvec-ref dvec i) lst) (- i 1)))) (define (dynvec->list dvec) (dynvec-to-list-rec dvec '() (- (dynvec-length dvec) 1)))