svd.scm 21 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735
  1. #| -*-Scheme-*-
  2. Copyright (C) 1986, 1987, 1988, 1989, 1990, 1991, 1992, 1993, 1994,
  3. 1995, 1996, 1997, 1998, 1999, 2000, 2001, 2002, 2003, 2004, 2005,
  4. 2006, 2007, 2008, 2009, 2010, 2011, 2012, 2013 Massachusetts
  5. Institute of Technology
  6. This file is part of MIT/GNU Scheme.
  7. MIT/GNU Scheme is free software; you can redistribute it and/or modify
  8. it under the terms of the GNU General Public License as published by
  9. the Free Software Foundation; either version 2 of the License, or (at
  10. your option) any later version.
  11. MIT/GNU Scheme is distributed in the hope that it will be useful, but
  12. WITHOUT ANY WARRANTY; without even the implied warranty of
  13. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
  14. General Public License for more details.
  15. You should have received a copy of the GNU General Public License
  16. along with MIT/GNU Scheme; if not, write to the Free Software
  17. Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301,
  18. USA.
  19. |#
  20. ;;;; Linear System Solver -- SVD -- Singular-Value Decomposition
  21. ;;; This file contains the following definitions:
  22. ;;;
  23. ;;; (svd-solve-linear-system A-matrix b-vector) => x-vector
  24. ;;; (svd-matrix-inverse A b succeed fail)
  25. ;;;
  26. ;;; (svd A continue)
  27. ;;; where continue = (lambda (U SIGMA V W)
  28. ;;; ;;A = U * SIGMA * (transpose V)
  29. ;;; ...)
  30. ;;; After execution the first n columns of U will contain
  31. ;;; left singular vectors, W be a vector of singular values,
  32. ;;; and V will contain right singular vectors. SIGMA will be
  33. ;;; a square matrix with the singular values on the diagonal.
  34. ;;; More precisely:
  35. ;;; Columns, j, of U whose wj are nonzero form an orthonormal basis
  36. ;;; for the range of A.
  37. ;;; Columns, j, of V whose qj are zero form an orthonormal basis for
  38. ;;; the null space of A.
  39. ;;; Note: These are solutions of the homogeneous equation A*x = 0
  40. (define (svd a continue)
  41. (svd-internal (matrix->array a)
  42. (lambda (u sigma v w)
  43. (continue (array->matrix u)
  44. (array->matrix sigma)
  45. (array->matrix v)
  46. w))))
  47. (define* (svd-least-squares a b #:optional eps)
  48. (if (default-object? eps) (set! eps 1e-15))
  49. (svd a
  50. (lambda (u sigma v w)
  51. (let ((inverted-w
  52. (let ((wmin
  53. (cond ((number? eps)
  54. (* eps (apply max (vector->list w))))
  55. ((procedure? eps)
  56. (* (eps w) (apply max (vector->list w))))
  57. (else
  58. (error "Bad cutoff -- SVD" eps)))))
  59. (make-initialized-vector (vector-length w)
  60. (lambda (i)
  61. (let ((wi (vector-ref w i)))
  62. (if (< wi wmin) 0 (/ 1 wi))))))))
  63. (matrix*vector v
  64. ((vector-elementwise *)
  65. (matrix*vector (m:transpose u) b)
  66. inverted-w))))))
  67. (define svd-solve-linear-system svd-least-squares)
  68. (define* (svd-invert a #:optional eps)
  69. (if (default-object? eps) (set! eps 1e-15))
  70. (svd a
  71. (lambda (u sigma v w)
  72. (let ((inverted-w
  73. (let ((wmin
  74. (cond ((number? eps)
  75. (* eps (apply max (vector->list w))))
  76. ((procedure? eps)
  77. (* (eps w) (apply max (vector->list w))))
  78. (else
  79. (error "Bad cutoff -- SVD" eps)))))
  80. (make-initialized-vector (vector-length w)
  81. (lambda (i)
  82. (let ((wi (vector-ref w i)))
  83. (if (< wi wmin) 0 (/ 1 wi))))))))
  84. (matrix*matrix v
  85. (matrix*matrix (m:make-diagonal inverted-w)
  86. (m:transpose u)))))))
  87. ;;; Singular-Value Decomposition
  88. ;;; Blind, ugly translation of Fortran SVD algorithm given in
  89. ;;; Forsythe, Malcolm, and Moler, "Computer Methods For Mathematical
  90. ;;; Computations", Chapter 9, Section 9.5, p.227.
  91. ;;; Obtained from RZ in Common Lisp
  92. ;;; and Transliterated to Scheme by GJS.
  93. ;;;
  94. ;;; Given m by n matrix A, compute the Singular Value Decomposition,
  95. ;;; A = U * SIGMA * (transpose V). A is not modified.
  96. ;;; After execution the first n columns of *SVD.U* will contain
  97. ;;; left singular vectors, *SVD.W* will contain singular values, and
  98. ;;; *SVD.V* will contain right singular vectors.
  99. ;;; FBE: start: initialize all variables
  100. (define* (svd-internal a continue #:optional matu matv)
  101. (if (default-object? matu) (set! matu true))
  102. (if (default-object? matv) (set! matv true))
  103. ;; continue = (lambda (u sigma v w) ...)
  104. (let* ((m (num-rows a)) (n (num-cols a))
  105. ;;(nm (max n m))
  106. (ierr 0)
  107. ;; (g) (scale) (anorm)
  108. ;; (l) (f) (h) (s)
  109. ;; (its) (flag1) (flag2) (l1) (c) (flag3) (k1)
  110. ;; (convergence)
  111. ;; (x) (y) (z)
  112. ;; (i)
  113. (g unspecific) (scale unspecific) (anorm unspecific)
  114. (l unspecific) (f unspecific) (h unspecific) (s unspecific)
  115. (its unspecific) (flag1 unspecific) (flag2 unspecific)
  116. (l1 unspecific) (c unspecific) (flag3 unspecific) (k1 unspecific)
  117. (convergence unspecific)
  118. (x unspecific) (y unspecific) (z unspecific)
  119. (i unspecific)
  120. (*svd.a* (array-copy a))
  121. (*svd.u* (array-copy a))
  122. (*svd.v* (generate-array n n (lambda (i j) 0)))
  123. (*svd.w* (make-vector n 0))
  124. (*svd.rv1* (make-vector n 0)))
  125. (set! g 0.0)
  126. (set! scale 0.0)
  127. (set! anorm 0.0)
  128. ;; Perform Householder bidiagonalization
  129. (do-up 0 n ;DO 300 I=1,N
  130. (lambda (i)
  131. (set! l (fix:+ i 1))
  132. ;; Perform column Householder
  133. ;; (write-line "column Householder")
  134. (vector-set! *svd.rv1* i (* scale g))
  135. (set! g 0.0)
  136. (set! s 0.0)
  137. (set! scale 0.0)
  138. (if (not (fix:> i (fix:- m 1)))
  139. (begin
  140. (do-up i m
  141. (lambda (k)
  142. (set! scale
  143. (+ scale
  144. (magnitude (array-ref *svd.u* k i))))))
  145. (if (not (zero? scale))
  146. (begin
  147. (do-up i m
  148. (lambda (k)
  149. (array-set! *svd.u* k i
  150. (/ (array-ref *svd.u* k i)
  151. scale))
  152. (set! s (+ s (square (array-ref *svd.u* k i))))))
  153. (set! f (array-ref *svd.u* i i))
  154. (set! g (if (negative? f) (sqrt s) (- (sqrt s))))
  155. (set! h (- (* f g) s))
  156. (array-set! *svd.u* i i (- f g))
  157. (if (not (fix:= i (fix:- n 1)))
  158. (do-up l n
  159. (lambda (j)
  160. (set! s 0.0)
  161. (do-up i m
  162. (lambda (k)
  163. (set! s
  164. (+ s
  165. (* (array-ref *svd.u* k i)
  166. (array-ref *svd.u* k j))))))
  167. (set! f (/ s h))
  168. (do-up i m
  169. (lambda (k)
  170. (array-set! *svd.u* k j
  171. (+ (array-ref *svd.u* k j)
  172. (* f (array-ref *svd.u* k i)))))))))
  173. (do-up i m
  174. (lambda (k)
  175. (array-set! *svd.u* k i (* scale (array-ref *svd.u* k i)))))))))
  176. (vector-set! *svd.w* i (* scale g))
  177. ;; Perform row Householder
  178. ;; (write-line "row Householder")
  179. (set! g 0.0) ;S210 + 1
  180. (set! s 0.0)
  181. (set! scale 0.0)
  182. (if (not (or (fix:> i (fix:- m 1)) (fix:= i (fix:- n 1))))
  183. (begin
  184. (do-up l n
  185. (lambda (k)
  186. (set! scale (+ scale (magnitude (array-ref *svd.u* i k))))))
  187. (if (not (zero? scale))
  188. (begin
  189. (do-up l n
  190. (lambda (k)
  191. (array-set! *svd.u* i k
  192. (/ (array-ref *svd.u* i k)
  193. scale))
  194. (set! s (+ s (square (array-ref *svd.u* i k))))))
  195. (set! f (array-ref *svd.u* i l))
  196. (set! g (if (negative? f) (sqrt s) (- (sqrt s))))
  197. (set! h (- (* f g) s))
  198. (array-set! *svd.u* i l (- f g))
  199. (do-up l n
  200. (lambda (k)
  201. (vector-set! *svd.rv1* k (/ (array-ref *svd.u* i k) h))))
  202. (if (not (fix:= i (fix:- m 1)))
  203. (do-up l m
  204. (lambda (j)
  205. (set! s 0.0)
  206. (do-up l n
  207. (lambda (k)
  208. (set! s
  209. (+ s
  210. (* (array-ref *svd.u* j k)
  211. (array-ref *svd.u* i k))))))
  212. (do-up l n
  213. (lambda (k)
  214. (array-set! *svd.u* j k
  215. (+ (array-ref *svd.u* j k)
  216. (* s (vector-ref *svd.rv1* k)))))))))
  217. (do-up l n
  218. (lambda (k)
  219. (array-set! *svd.u* i k (* scale (array-ref *svd.u* i k)))))))))
  220. (set! anorm
  221. (max anorm
  222. (+ (magnitude (vector-ref *svd.w* i))
  223. (magnitude (vector-ref *svd.rv1* i)))))))
  224. ;;S300
  225. ;; Accumulation of right-hand transformations
  226. (if matv
  227. (do-down (fix:- n 1) -1
  228. (lambda (i)
  229. (if (not (fix:= i (fix:- n 1)))
  230. (begin
  231. (if (not (= g 0.0))
  232. (begin
  233. (do-up l n
  234. (lambda (j)
  235. (array-set! *svd.v* j i
  236. (/ (/ (array-ref *svd.u* i j)
  237. (array-ref *svd.u* i l))
  238. g))))
  239. (do-up l n
  240. (lambda (j)
  241. (set! s 0.0)
  242. (do-up l n
  243. (lambda (k)
  244. (set! s (+ s (* (array-ref *svd.u* i k)
  245. (array-ref *svd.v* k j))))))
  246. (do-up l n
  247. (lambda (k)
  248. (array-set! *svd.v* k j
  249. (+ (array-ref *svd.v* k j)
  250. (* s (array-ref *svd.v* k i))))))))))
  251. (do-up l n
  252. (lambda (j)
  253. (array-set! *svd.v* i j 0.0)
  254. (array-set! *svd.v* j i 0.0)))))
  255. (array-set! *svd.v* i i 1.0)
  256. (set! g (vector-ref *svd.rv1* i))
  257. (set! l i))))
  258. ;; Accumulation of left-hand transformations
  259. (if matu
  260. (do-down (fix:- (if (fix:< m n) m n) 1) -1
  261. (lambda (i)
  262. (set! l (fix:+ i 1))
  263. (set! g (vector-ref *svd.w* i))
  264. (if (not (fix:= i (fix:- n 1)))
  265. (do-up l n
  266. (lambda (j)
  267. (array-set! *svd.u* i j 0.0))))
  268. (if (not (zero? g))
  269. (begin
  270. (if (not (fix:= i (fix:- (if (fix:< m n) m n) 1)))
  271. (do-up l n
  272. (lambda (j)
  273. (set! s 0.0)
  274. (do-up l m
  275. (lambda (k)
  276. (set! s (+ s (* (array-ref *svd.u* k i)
  277. (array-ref *svd.u* k j))))))
  278. (set! f (/ (/ s (array-ref *svd.u* i i)) g))
  279. (do-up i m
  280. (lambda (k)
  281. (array-set! *svd.u* k j
  282. (+ (array-ref *svd.u* k j)
  283. (* f (array-ref *svd.u* k i)))))))))
  284. (do-up i m
  285. (lambda (j)
  286. (array-set! *svd.u* j i (/ (array-ref *svd.u* j i) g)))))
  287. (do-up i m
  288. (lambda (j)
  289. (array-set! *svd.u* j i 0.0))))
  290. (array-set! *svd.u* i i (+ (array-ref *svd.u* i i) 1.0)))))
  291. ;; Bidiagonalization complete
  292. ;; (write-line "Bidiagonal form (diagonal followed by superdiagonal):")
  293. ;; (write-line *svd.w*)
  294. ;; (write-line *svd.rv1*)
  295. ;; Diagonalization of bidiagonal form
  296. (do-down (- n 1) -1
  297. (lambda (k)
  298. (set! k1 (fix:- k 1))
  299. (set! its 0)
  300. (set! flag1 false)
  301. (set! flag2 false)
  302. (set! convergence false)
  303. (let lp ()
  304. (if (not convergence)
  305. (begin
  306. (set! flag1 false)
  307. (set! flag2 false)
  308. (let ll-lp ((ll k))
  309. (if (not (or (fix:< l 0) flag1 flag2))
  310. (begin
  311. (set! l ll)
  312. (set! l1 (fix:- l 1))
  313. (set! flag1 (= (+ (magnitude (vector-ref *svd.rv1* l)) anorm) anorm))
  314. (if (not flag1)
  315. (set! flag2
  316. (= (+ (magnitude (vector-ref *svd.w* l1))
  317. anorm)
  318. anorm)))
  319. (ll-lp (fix:- ll 1)))))
  320. (if (not flag1)
  321. (begin
  322. (set! c 0.0)
  323. (set! s 1.0)
  324. (set! flag3 false)
  325. (let i-lp ((i l))
  326. (if (not (or (fix:> i k) flag3))
  327. (begin
  328. (set! f (* s (vector-ref *svd.rv1* i)))
  329. (vector-set! *svd.rv1* i (* c (vector-ref *svd.rv1* i)))
  330. (set! flag3 (= (+ (magnitude f) anorm) anorm))
  331. (if (not flag3)
  332. (begin
  333. (set! g (vector-ref *svd.w* i))
  334. (set! h (sqrt (+ (* f f) (* g g))))
  335. (vector-set! *svd.w* i h)
  336. (set! c (/ g h))
  337. (set! s (/ (- f) h))
  338. (if matu
  339. (do ((j 0 (fix:+ j 1)))
  340. ((fix:= j m))
  341. (set! y (array-ref *svd.u* j l1))
  342. (set! z (array-ref *svd.u* j i))
  343. (array-set! *svd.u* j l1 (+ (* y c) (* z s)))
  344. (array-set! *svd.u* j i (+ (* (- y) s) (* z c)))))))
  345. (i-lp (fix:+ i 1)))))))
  346. ;; test for convergence
  347. (set! z (vector-ref *svd.w* k))
  348. (cond ((fix:= l k)
  349. (set! convergence true))
  350. (else
  351. (if (fix:= its 30)
  352. (error "SVD: No convergence after 30 iterations."))
  353. (set! its (1+ its))
  354. (set! x (vector-ref *svd.w* l))
  355. (set! y (vector-ref *svd.w* k1))
  356. (set! g (vector-ref *svd.rv1* k1))
  357. (set! h (vector-ref *svd.rv1* k))
  358. (set! f (/ (+ (* (- y z) (+ y z)) (* (- g h) (+ g h)))
  359. (* 2.0 h y)))
  360. (set! g (sqrt (+ (square f) 1.0)))
  361. (set! f (/ (+ (* (- x z) (+ x z))
  362. (* h
  363. (-
  364. (/ y (+ f (if (negative? f) (- g) g)))
  365. h)))
  366. x))
  367. (set! c 1.0)
  368. (set! s 1.0)
  369. (do-up l (fix:+ k1 1)
  370. (lambda (i1)
  371. (set! i (fix:+ i1 1))
  372. (set! g (vector-ref *svd.rv1* i))
  373. (set! y (vector-ref *svd.w* i))
  374. (set! h (* s g))
  375. (set! g (* c g))
  376. (set! z (sqrt (+ (square f) (square h))))
  377. (vector-set! *svd.rv1* i1 z)
  378. (set! c (/ f z))
  379. (set! s (/ h z))
  380. (set! f (+ (* x c) (* g s)))
  381. (set! g (+ (* (- x) s) (* g c)))
  382. (set! h (* y s))
  383. (set! y (* y c))
  384. (if matv
  385. (do-up 0 n
  386. (lambda (j)
  387. (set! x (array-ref *svd.v* j i1))
  388. (set! z (array-ref *svd.v* j i))
  389. (array-set! *svd.v* j i1 (+ (* x c) (* z s)))
  390. (array-set! *svd.v* j i (+ (* (- x) s) (* z c))))))
  391. (set! z (sqrt (+ (square f) (square h))))
  392. (vector-set! *svd.w* i1 z)
  393. (if (not (zero? z))
  394. (begin (set! c (/ f z))
  395. (set! s (/ h z))))
  396. (set! f (+ (* c g) (* s y)))
  397. (set! x (+ (* (- s) g) (* c y)))
  398. (if matu
  399. (do-up 0 m
  400. (lambda (j)
  401. (set! y (array-ref *svd.u* j i1))
  402. (set! z (array-ref *svd.u* j i))
  403. (array-set! *svd.u* j i1 (+ (* y c) (* z s)))
  404. (array-set! *svd.u* j i (+ (* (- y) s) (* z c))))))))
  405. (vector-set! *svd.rv1* l 0.0)
  406. (vector-set! *svd.rv1* k f)
  407. (vector-set! *svd.w* k x)
  408. (set! convergence false)))
  409. (lp))))
  410. ;; convergence
  411. (if (< z 0.0)
  412. (begin (vector-set! *svd.w* k (- z))
  413. (if matv
  414. (do-up 0 n
  415. (lambda (j)
  416. (array-set! *svd.v* j k (- (array-ref *svd.v* j k))))))))))
  417. ;; Set *svd.a* to be the matrix of singular values
  418. (set! *svd.a* (generate-array n n (lambda (i j) 0)))
  419. (do-up 0 n
  420. (lambda (i)
  421. (array-set! *svd.a* i i (vector-ref *svd.w* i))))
  422. (continue *svd.u* *svd.a* *svd.v* *svd.w*)))
  423. #|;;; Test case from book.
  424. (define a
  425. #( #( 1 6 11 )
  426. #( 2 7 12 )
  427. #( 3 8 13 )
  428. #( 4 9 14 )
  429. #( 5 10 15 ) ))
  430. (pp (svd a list))
  431. (#(#(-.35455705703768087 -.6886866437682524 .5623498172874758)
  432. #(-.39869636999883223 -.3755545293958711 -.6404098216452332)
  433. #(-.4428356829599836 -.06242241502349071 4.3232194451219827e-4)
  434. #(-.48697499592113497 .2507096993488898 -.32903444810323323)
  435. #(-.5311143088822865 .5638418137212697 .40666213051647754))
  436. #(#(35.127223333574676 0 0)
  437. #(0 2.4653966969165197 0)
  438. #(0 0 2.839772892390358e-15))
  439. #(#(-.201664911192694 .8903171327830188 .4082482904638638)
  440. #(-.5168305013923045 .2573316268240516 -.816496580927726)
  441. #(-.8319960915919149 -.3756538791349179 .40824829046386263))
  442. #(35.127223333574676 2.4653966969165197 2.839772892390358e-15))
  443. |#
  444. #|
  445. ;;; From Golub and Reinsch in Wilkinson&Reinsch Handbook for Automatic
  446. ;;; Computation -- Linear Algebra Vol II, p.150.
  447. (define a
  448. (m:generate 20 21
  449. (lambda (i j)
  450. (cond ((> i j) 0.0)
  451. ((= i j) (- 20.0 i))
  452. ((< i j) -1.0)))))
  453. (pp (cadddr (svd a list)))
  454. #(20.4939015319192 19.493588689617948 3.5665073441521055e-27
  455. 18.49324200890693 17.492855684535876 16.492422502470617
  456. 15.491933384829649 14.491376746189422 13.49073756323204
  457. 12.489995996796784 11.489125293076066 10.48808848170151
  458. 9.486832980505142 8.48528137423857 7.483314773547884
  459. 3.4641016151377517 6.480740698407856 4.47213595499958
  460. 5.477225575051661 2.4494897427831783 1.414213562373095)
  461. ;;; Singular values should be:
  462. (define (sig j)
  463. (let ((k (- 21 j)))
  464. (sqrt (* k (+ k 1)))))
  465. (sig 20)
  466. ;Value: 1.4142135623730951
  467. (sig 1)
  468. ;Value: 20.493901531919196
  469. (sig 2)
  470. ;Value: 19.493588689617926
  471. (sig 3)
  472. ;Value: 18.49324200890693
  473. (sig 4)
  474. ;Value: 17.4928556845359
  475. (sig 20)
  476. ;Value: 1.4142135623730951
  477. (sig 21)
  478. ;Value: 0
  479. ;;; From Golub and Reinsch in Wilkinson&Reinsch Handbook for Automatic
  480. ;;; Computation -- Linear Algebra Vol II, p.150.
  481. (define a
  482. (m:generate 30 30
  483. (lambda (i j)
  484. (cond ((> i j) 0.0)
  485. ((= i j) 1.0)
  486. ((< i j) -1.0)))))
  487. (pp (cadddr (svd a list)))
  488. #(18.202905557529274 6.2231965226042325 3.9134802033356157 2.976794502557797
  489. 2.4904506296603617 2.7939677151340594e-9 2.2032075744799298 2.0191836540545935
  490. 1.8943415476856935 1.8059191266123142 1.7411357677479578 1.6923565443952688
  491. 1.654793027369345 1.6253208928779395 1.6018333566662764 1.5828695887137096
  492. 1.5673921444800174 1.55464889010938 1.5440847140760587 1.5352835655449113
  493. 1.5279295121603145 1.5217800390635037 1.5166474128367937 1.5123854738997016
  494. 1.508880156801892 1.5060426207239777 1.5038042438126578 1.5002314347754444
  495. 1.5021129767540111 1.5009307119770665)
  496. |#
  497. #| ;;; Testing
  498. (define (matnorm a)
  499. (apply max
  500. (map abs
  501. (apply append
  502. (map vector->list
  503. (vector->list (matrix->array a)))))))
  504. (define* (test n #:optional m)
  505. (if (default-object? m)
  506. (set! m 100))
  507. (let ((h (lu-hilbert n)))
  508. (write-line `(lu ,(matnorm
  509. (matrix-matrix (matrix*matrix h (lu-invert h))
  510. (m:make-identity n)))))
  511. (svd h
  512. (lambda (u sigma v w)
  513. (let elp ((eps 1e-10) (m m))
  514. (if (fix:= m 0)
  515. 'done
  516. (let ((inverted-w
  517. (let ((wmin (* eps (apply max (vector->list w)))))
  518. (make-initialized-vector (vector-length w)
  519. (lambda (i)
  520. (let ((wi (vector-ref w i)))
  521. (if (< wi wmin) 0 (/ 1 wi))))))))
  522. (let ((inv
  523. (matrix*matrix v
  524. (matrix*matrix (m:make-diagonal inverted-w)
  525. (m:transpose u)))))
  526. (write-line `(svd ,eps
  527. ,(matnorm
  528. (matrix-matrix (matrix*matrix h inv)
  529. (m:make-identity n))))))
  530. (elp (/ eps 3) (fix:- m 1)))))))))
  531. ;;; Before 13 LU is better than SVD, but SVD eventually wins.
  532. (test 13)
  533. (lu .90625)
  534. (svd .0000000001 .6675129055220168)
  535. (svd 3.3333333333333335e-11 .6000871658325195)
  536. (svd 1.1111111111111111e-11 .6000871658325195)
  537. (svd 3.703703703703703e-12 .6000871658325195)
  538. (svd 1.2345679012345677e-12 .5423380881547928)
  539. (svd 4.115226337448559e-13 .5423380881547928)
  540. (svd 1.371742112482853e-13 .5423380881547928)
  541. (svd 4.572473708276176e-14 .5423380881547928)
  542. (svd 1.5241579027587254e-14 .4376716613769531)
  543. (svd 5.0805263425290845e-15 .4376716613769531)
  544. (svd 1.6935087808430282e-15 .4376716613769531)
  545. (svd 5.64502926947676e-16 .4376716613769531)
  546. (svd 1.88167642315892e-16 .4376716613769531)
  547. (svd 6.272254743863067e-17 .348388671875)
  548. (svd 2.0907515812876892e-17 .348388671875)
  549. (svd 6.96917193762563e-18 .348388671875)
  550. (svd 2.3230573125418768e-18 2.515625)
  551. (svd 7.74352437513959e-19 2.515625)
  552. (svd 2.5811747917131964e-19 2.515625)
  553. (svd 8.603915972377322e-20 2.515625)
  554. (svd 2.867971990792441e-20 2.515625)
  555. (svd 9.559906635974802e-21 2.515625)
  556. (svd 3.186635545324934e-21 2.515625)
  557. (svd 1.0622118484416447e-21 2.515625)
  558. (svd 3.540706161472149e-22 2.515625)
  559. (svd 1.180235387157383e-22 2.515625)
  560. ;Quit!
  561. (test 19)
  562. (lu 4.875)
  563. (svd .0000000001 .7776952391723171)
  564. (svd 3.3333333333333335e-11 .7395966090261936)
  565. (svd 1.1111111111111111e-11 .7395966090261936)
  566. (svd 3.703703703703703e-12 .7395966090261936)
  567. (svd 1.2345679012345677e-12 .6962781026959419)
  568. (svd 4.115226337448559e-13 .6962781026959419)
  569. (svd 1.371742112482853e-13 .6962781026959419)
  570. (svd 4.572473708276176e-14 .6577432155609131)
  571. (svd 1.5241579027587254e-14 .6577432155609131)
  572. (svd 5.0805263425290845e-15 .6577432155609131)
  573. (svd 1.6935087808430282e-15 .6577432155609131)
  574. (svd 5.64502926947676e-16 .5989990234375)
  575. (svd 1.88167642315892e-16 .5989990234375)
  576. (svd 6.272254743863067e-17 .5989990234375)
  577. (svd 2.0907515812876892e-17 .90625)
  578. (svd 6.96917193762563e-18 .90625)
  579. (svd 2.3230573125418768e-18 22.3125)
  580. (svd 7.74352437513959e-19 22.3125)
  581. ;Quit!
  582. (test 20)
  583. (lu 34.)
  584. (svd .0000000001 .752550782635808)
  585. (svd 3.3333333333333335e-11 .752550782635808)
  586. (svd 1.1111111111111111e-11 .752550782635808)
  587. (svd 3.703703703703703e-12 .752550782635808)
  588. (svd 1.2345679012345677e-12 .7140587568283081)
  589. (svd 4.115226337448559e-13 .7140587568283081)
  590. (svd 1.371742112482853e-13 .7140587568283081)
  591. (svd 4.572473708276176e-14 .6803770065307617)
  592. (svd 1.5241579027587254e-14 .6803770065307617)
  593. (svd 5.0805263425290845e-15 .6803770065307617)
  594. (svd 1.6935087808430282e-15 .643280029296875)
  595. (svd 5.64502926947676e-16 .643280029296875)
  596. (svd 1.88167642315892e-16 .643280029296875)
  597. (svd 6.272254743863067e-17 .643280029296875)
  598. (svd 2.0907515812876892e-17 .59033203125)
  599. (svd 6.96917193762563e-18 .59033203125)
  600. (svd 2.3230573125418768e-18 13.)
  601. (svd 7.74352437513959e-19 24.)
  602. (svd 2.5811747917131964e-19 24.)
  603. ;Quit!
  604. (test 30)
  605. (lu 12.25)
  606. (svd .0000000001 .8594314045330975)
  607. (svd 3.3333333333333335e-11 .8390090614557266)
  608. (svd 1.1111111111111111e-11 .8390090614557266)
  609. (svd 3.703703703703703e-12 .8144026100635529)
  610. (svd 1.2345679012345677e-12 .8144026100635529)
  611. (svd 4.115226337448559e-13 .8144026100635529)
  612. (svd 1.371742112482853e-13 .7979546785354614)
  613. (svd 4.572473708276176e-14 .7979546785354614)
  614. (svd 1.5241579027587254e-14 .7979546785354614)
  615. (svd 5.0805263425290845e-15 .7774620056152344)
  616. (svd 1.6935087808430282e-15 .7774620056152344)
  617. (svd 5.64502926947676e-16 .7774620056152344)
  618. (svd 1.88167642315892e-16 .7529296875)
  619. (svd 6.272254743863067e-17 .7529296875)
  620. (svd 2.0907515812876892e-17 .7529296875)
  621. (svd 6.96917193762563e-18 5.703125)
  622. (svd 2.3230573125418768e-18 13.203125)
  623. (svd 7.74352437513959e-19 31.8125)
  624. (svd 2.5811747917131964e-19 34.3359375)
  625. ;Quit!
  626. ;;; Singular values for (hilbert 30) are:
  627. #(1.6046959983598275 .3344360125333556 .05091302233254397
  628. 6.612384688874973e-3 7.527825195740986e-4 7.593680264534132e-5
  629. 6.834096698733383e-6 5.513422736482628e-7 4.000480673281162e-8
  630. 2.6164842785734506e-9 1.5446121110479932e-10 8.235086631801633e-12
  631. 3.964803127460767e-13 1.7223602006838723e-14 6.6921268878625e-16
  632. 2.4447558436546055e-17 9.074602910397975e-18 5.985016835530655e-18
  633. 5.7110319490636254e-18 1.1209774921001327e-17 7.86180746543282e-18
  634. 7.113462016773155e-18 5.4562440222629994e-18 3.964051053484464e-18
  635. 4.899374346302087e-18 3.7838677932677645e-18 3.1519489253291782e-18
  636. 2.852971370421691e-18 1.9386313723000905e-18 9.527265084040377e-19)
  637. |#