(define (array-ref a . xs)
  (or (array:array? a)
      (error "not an array"))
  (let ((shape (array:shape a)))
    (if (null? xs)
        (array:check-indices "array-ref" '() shape)
        (let ((x (car xs)))
          (if (vector? x)
              (array:check-index-vector "array-ref" x shape)
              (if (integer? x)
                  (array:check-indices "array-ref" xs shape)
                  (if (array:array? x)
                      (array:check-index-actor "array-ref" x shape)
                      (error "not an index object"))))))
    (vector-ref
     (array:vector a)
     (if (null? xs)
         ((array:index a))
         (let ((x (car xs)))
           (if (vector? x)
               (array:index/vector
                (quotient (vector-length shape) 2)
                (array:index a)
                x)
               (if (integer? x)
                   (apply (array:index a) xs)
                   (if (array:array? x)
                       (array:index/array
                        (quotient (vector-length shape) 2)
                        (array:index a)
                        (array:vector x)
                        (array:index x))
                       (error "array-ref: bad index object")))))))))

(define (array-set! a x . xs)
  (or (array:array? a)
      (error "not an array"))
  (let ((shape (array:shape a)))
    (if (null? xs)
        (array:check-indices "array-set!" '() shape)
        (if (vector? x)
            (array:check-index-vector "array-set!" x shape)
            (if (integer? x)
                (array:check-indices.o "array-set!" (cons x xs) shape)
                (if (array:array? x)
                    (array:check-index-actor "array-set!" x shape)
                    (error "not an index object")))))
    (call-with-values
     (lambda ()
       (if (null? xs)
           ((array:index a) x)
           (if (vector? x)
               (values
                (array:index/vector
                 (quotient (vector-length shape) 2)
                 (array:index a)
                 x)
                (car xs))
               (if (integer? x)
                   (apply (array:index a) x xs)
                   (if (array:array? x)
                       (values
                        (array:index/array
                         (quotient (vector-length shape) 2)
                         (array:index a)
                         (array:vector x)
                         (array:index x))
                        (car xs))
                       (error "array:set!: bad index object"))))))
     (lambda (k o)
       (vector-set! (array:vector a) k o)))))
