racket/collects/math/private/matrix/matrix-expt.rkt
Neil Toronto 155ec7dc41 Reviewing and refactoring `math/matrix', part 1
* Finally added `array-axis-expand' as a dual for `array-axis-reduce'
  in order to implement `vandermonde-matrix' elegantly

* Better, shorter matrix multiply; reworked all matrix arithmetic

* Split "matrix-operations.rkt" into at least 5 parts:
 * "matrix-operations.rkt"
 * "matrix-basic.rkt"
 * "matrix-comprehension.rkt"
 * "matrix-sequences.rkt"
 * "matrix-column.rkt"

Added "matrix-constructors.rkt"

Added `matrix', `row-matrix', and `col-matrix' macros

A lot of other little changes

Currently, `in-row' and `in-column' are broken. I intend to implement
them in a way that makes them work in untyped and Typed Racket.
2012-12-20 17:32:16 -07:00

22 lines
836 B
Racket

#lang typed/racket
(require math/array
"matrix-types.rkt"
"matrix-constructors.rkt"
"matrix-arithmetic.rkt")
(provide matrix-expt)
(: matrix-expt : (Matrix Number) Integer -> (Matrix Number))
(define (matrix-expt a n)
(cond [(not (square-matrix? a)) (raise-argument-error 'matrix-expt "square-matrix?" 0 a n)]
[(negative? n) (raise-argument-error 'matrix-expt "Natural" 1 a n)]
[(zero? n) (identity-matrix (square-matrix-size a))]
[else
(let: loop : (Matrix Number) ([n : Positive-Integer n])
(cond [(= n 1) a]
[(= n 2) (matrix* a a)]
[(even? n) (let ([a^n/2 (matrix-expt a (quotient n 2))])
(matrix* a^n/2 a^n/2))]
[else (matrix* a (matrix-expt a (sub1 n)))]))]))