1function test_errors
2%TEST_ERRORS tests error handling for the factorize object methods
3%
4% Example
5%   test_errors
6%
7% See also test_all, factorize.
8
9% Copyright 2011-2012, Timothy A. Davis, http://www.suitesparse.com
10
11fprintf ('\nTesting error handling (error messages are expected)\n\n') ;
12reset_rand ;
13ok = true ;
14
15% the matrix A must be 2D for factorize
16A = ones (2,2,2) ;
17try
18    F = factorize (A, [ ], 1) ;                                             %#ok
19    ok = false ;
20    fprintf ('error not caught: A must be 2D for factorize\n') ;
21catch me
22    fprintf ('Expected error: [%s]\n', me.message) ;
23end
24
25% check if invalid strategy is caught
26A = rand (4) ;
27try
28    F = factorize (A, 'gunk', 1) ;                                          %#ok
29    ok = false ;
30    fprintf ('error not caught: invalid strategy\n') ;
31catch me
32    fprintf ('Expected error: [%s]\n', me.message) ;
33end
34
35% cannot use COD on sparse matrices
36try
37    [U, R, V, r] = cod (sparse (A)) ;                                       %#ok
38    ok = false ;
39    fprintf ('error not caught: cannot use cod for sparse A\n') ;
40catch me
41    fprintf ('Expected error: [%s]\n', me.message) ;
42end
43
44% cannot use RQ on sparse matrices
45try
46    [R, Q] = rq (sparse (A)) ;                                              %#ok
47    ok = false ;
48    fprintf ('error not caught: cannot use rq for sparse A\n') ;
49catch me
50    fprintf ('Expected error: [%s]\n', me.message) ;
51end
52
53% cannot do B\inverse(A) or inverse(A)/B
54A = rand (2) ;
55B = rand (2) ;
56try
57    C = B \ inverse (A) ;                                                   %#ok
58    ok = false ;
59    fprintf ('error not caught: requires explicit inverseA\n') ;
60catch me
61    fprintf ('Expected error: [%s]\n', me.message) ;
62end
63try
64    C = inverse (A) / B ;                                                   %#ok
65    ok = false ;
66    fprintf ('error not caught: requires explicit inverseA\n') ;
67catch me
68    fprintf ('Expected error: [%s]\n', me.message) ;
69end
70
71% cannot use COD_SPARSE on full matrices
72try
73    [U, R, V, r] = cod_sparse (A) ;                                         %#ok
74    ok = false ;
75    fprintf ('error not caught: cannot use cod_sparse for full A\n') ;
76catch me
77    fprintf ('Expected error: [%s]\n', me.message) ;
78end
79
80if (~ok)
81    error ('!') ;
82end
83
84% cannot factorize a logical array, sparse or full
85for s = {'default', 'symmetric', 'qr', 'lu', 'ldl', 'chol', 'svd', 'cod'}
86    for sp = 0:1
87        A = logical (ones (3)) ;                                            %#ok
88        if (sp)
89            A = sparse (A) ;
90        end
91        try
92            F = factorize (A, char (s), 1) ;                                %#ok
93            ok = false ;
94            fprintf ('error not caught:\n') ;
95        catch me
96            fprintf ('\nExpected error: [%s]\n', me.message) ;
97        end
98    end
99end
100try
101    A = logical (sparse (rand (3,4))) ;
102    F = factorize (A, 'qr', 1) ;                                            %#ok
103    ok = false ;
104    fprintf ('error not caught:\n') ;
105catch me
106    fprintf ('\nExpected error: [%s]\n', me.message) ;
107end
108
109if (~ok)
110    error ('!') ;
111end
112
113% the matrix A must be full-rank for ldl and chol
114for s = {'ldl', 'chol'}
115    for sp = 0:1
116        A = ones (3) ;
117        if (sp)
118            A = sparse (A) ;
119        end
120        try
121            F = factorize (A, char (s), 1) ;                                %#ok
122            ok = false ;
123            fprintf ('error not caught\n') ;
124        catch                                                               %#ok
125        end
126        A = zeros (3,2) ;
127        if (sp)
128            A = sparse (A) ;
129        end
130        try
131            F = factorize (A, char (s), 1) ;                                %#ok
132            ok = false ;
133            fprintf ('error not caught\n') ;
134        catch                                                               %#ok
135        end
136        A = zeros (2,3) ;
137        if (sp)
138            A = sparse (A) ;
139        end
140        try
141            F = factorize (A, char (s), 1) ;                                %#ok
142            ok = false ;
143            fprintf ('error not caught\n') ;
144        catch                                                               %#ok
145        end
146    end
147end
148
149% cannot do LU, CHOL, or LDL on rectangular matrices
150for s = {'lu', 'ldl', 'chol'}
151    A = rand (3,2) ;
152    for sp = 0:1
153        try
154            F = factorize (A, char (s), 1) ;                                %#ok
155            ok = false ;
156            fprintf ('\nerror not caught: tall-and-thin case\n') ;
157        catch me
158            fprintf ('\nExpected error: [%s]\n', me.message) ;
159        end
160        A = sparse (A) ;
161    end
162end
163
164if (~ok)
165    error ('!') ;
166end
167
168% cannot do QR on short-and-fat matrices or QRT on tall-and-thin matrices
169try
170    F = factorization_qr_dense (rand (2,3), 0) ;                            %#ok
171    ok = false ;
172    fprintf ('\nerror not caught: short-and-fat case\n') ;
173catch me
174   fprintf ('\nExpected error: [%s]\n', me.message) ;
175end
176try
177    F = factorization_qr_sparse (sparse (rand (2,3)), 0) ;                  %#ok
178    ok = false ;
179    fprintf ('\nerror not caught: short-and-fat case\n') ;
180catch me
181   fprintf ('\nExpected error: [%s]\n', me.message) ;
182end
183try
184    F = factorization_qrt_dense (rand (3,2), 0) ;                           %#ok
185    ok = false ;
186    fprintf ('\nerror not caught: tall-and-thin case\n') ;
187catch me
188   fprintf ('\nExpected error: [%s]\n', me.message) ;
189end
190try
191    F = factorization_qrt_sparse (sparse (rand (3,2)), 0) ;                 %#ok
192    ok = false ;
193    fprintf ('\nerror not caught: tall-and-thin case\n') ;
194catch me
195   fprintf ('\nExpected error: [%s]\n', me.message) ;
196end
197
198if (~ok)
199    error ('!') ;
200end
201
202% cannot do CHOL, or LDL on singular matrices
203for s = {'ldl', 'chol'}
204    A = zeros (2) ;
205    for sp = 0:1
206        try
207            F = factorize (A, char (s), 1) ;                                %#ok
208            ok = false ;
209            fprintf ('\nerror not caught: singular case\n') ;
210        catch me
211            fprintf ('\nExpected error: [%s]\n', me.message) ;
212        end
213        A = sparse (A) ;
214    end
215end
216
217if (~ok)
218    error ('!') ;
219end
220
221% cannot use cell indexing
222A = rand (3,2) ;
223F = factorize (A, [ ], 1) ;
224try
225    C = F {1} ;                                                        %#ok
226    ok = false ;
227    fprintf ('\nerror not caught: cannot use cell indexing\n') ;
228catch me
229    fprintf ('\nExpected error: [%s]\n', me.message) ;
230end
231
232% invalid indexing
233try
234    C = F (1,1).L ;                                                    %#ok
235    ok = false ;
236    fprintf ('error not caught: invalid indexing\n') ;
237catch me
238    fprintf ('Expected error: [%s]\n', me.message) ;
239end
240
241% invalid indexing
242try
243    C = F.L (1,1).stuff ;                                              %#ok
244    ok = false ;
245    fprintf ('error not caught: invalid indexing\n') ;
246catch me
247    fprintf ('Expected error: [%s]\n', me.message) ;
248end
249
250% non-existent field
251try
252    C = F.junk ;                                                       %#ok
253    ok = false ;
254    fprintf ('error not caught: invalid field\n') ;
255catch me
256    fprintf ('Expected error: [%s]\n', me.message) ;
257end
258
259% can only update/downdate a dense Cholesky factorization
260A = rand (2) ;
261F = factorize (A, [ ], 1) ;
262w = rand (2,1) ;
263try
264    F = cholupdate (F,w) ;
265    fprintf ('error not caught: cannot update this type of matrix\n') ;
266    disp (F) ;
267    ok = false ;
268catch me
269    fprintf ('\nExpected error: [%s]\n', me.message) ;
270end
271try
272    F = choldowndate (F,w,'-') ;
273    fprintf ('error not caught: cannot downdate this type of matrix\n') ;
274    disp (F) ;
275    ok = false ;
276catch me
277    fprintf ('Expected error: [%s]\n', me.message) ;
278end
279
280% cannot do condest(F) or cond(F,1) for rectangular matrices
281try
282    F = factorize (rand (4,3)) ;
283    c = condest (F) ;                                                       %#ok
284    ok = false ;
285    fprintf ('\nerror not caught: condest for rectangular case\n') ;
286catch me
287   fprintf ('\nExpected error: [%s]\n', me.message) ;
288end
289try
290    F = factorize (rand (4,3), 'svd') ;
291    c = cond (F,1) ;                                                        %#ok
292    ok = false ;
293    fprintf ('\nerror not caught: cond(A,1) for rectangular case\n') ;
294catch me
295   fprintf ('\nExpected error: [%s]\n', me.message) ;
296end
297
298% test for invalid kind of svd
299try
300    F = factorize (rand (4,3), 'svd') ;
301    [U, S, V] = svd (F,'gunk') ;                                            %#ok
302    ok = false ;
303    fprintf ('\nerror not caught: invalid kind of svd\n') ;
304catch me
305   fprintf ('\nExpected error: [%s]\n', me.message) ;
306end
307
308% test for invalid cholupdate parameter
309try
310    A = rand (2) ;
311    A = A*A' ;
312    F = factorize (A) ;
313    G = cholupdate (F, ones(2,1), 'gunk') ;                                 %#ok
314    ok = false ;
315    fprintf ('\nerror not caught: invalid kind of cholupdate\n') ;
316catch me
317   fprintf ('\nExpected error: [%s]\n', me.message) ;
318end
319
320%-------------------------------------------------------------------------------
321
322if (~ok)
323    error ('error-handling failed') ;
324end
325fprintf ('\nAll error-handing tests passed\n') ;
326