Macaulay2 Engine
Loading...
Searching...
No Matches
eigen.cpp
Go to the documentation of this file.
1//#define NO_LAPACK
2/*
3Uncommenting the above has two consequences:
4 (1) This effectively eliminates the use of LAPACK (eigen is used instead for machine precision).
5 (2) This slows down the compilation (at the moment) due to heavy templating in eigen.
6*/
7
8#include <cstdlib>
9
10#include <M2/math-include.h>
11
12// the reason for the following is that mpreal.h defines a namespace mpfr,
13// which conflicts with mpfr defined by us
14#define mpfr eigen_mpfr
15#include "mpreal.h"
16#include <unsupported/Eigen/MPRealSupport>
17#undef mpfr
18
19#include <Eigen/SVD>
20#include <Eigen/Eigenvalues>
21#include "eigen.hpp"
22
23using Real = eigen_mpfr::mpreal;
24using Complex = std::complex<Real>;
25using MatrixXmpRRR = Eigen::Matrix<Real,Eigen::Dynamic,Eigen::Dynamic>;
26using MatrixXmpCCC = Eigen::Matrix<Complex,Eigen::Dynamic,Eigen::Dynamic>;
27#ifdef NO_LAPACK
28using MatrixXmpRR = Eigen::Matrix<double,Eigen::Dynamic,Eigen::Dynamic>;
29using MatrixXmpCC = Eigen::Matrix<std::complex<double>,Eigen::Dynamic,Eigen::Dynamic>;
30#endif
31
32#ifdef _LIBCPP_VERSION
33/* workaround incompatibility between libc++'s implementation of complex and
34 * mpreal
35 */
36namespace eigen_mpfr {
37inline Real abs(const Complex &x) { return hypot(x.real(), x.imag()); }
38inline Complex sqrt(const Complex &x)
39{
40 Real a = abs(x);
41 const Real &xr = x.real();
42 const Real &xi = x.imag();
43 if (xi >= 0) { return Complex(sqrt((a + xr) / 2), sqrt((a - xr) / 2)); }
44 else { return Complex(sqrt((a + xr) / 2), -sqrt((a - xr) / 2)); }
45}
46inline Complex operator/(const Complex &lhs, const Complex &rhs)
47{
48 const Real &lhsr = lhs.real();
49 const Real &lhsi = lhs.imag();
50 const Real &rhsr = rhs.real();
51 const Real &rhsi = rhs.imag();
52 Real normrhs = rhsr*rhsr+rhsi*rhsi;
53 return Complex((lhsr * rhsr + lhsi * rhsi) / normrhs,
54 (lhsi * rhsr - lhsr * rhsi) / normrhs);
55}
56inline Complex operator*(const Complex &lhs, const Complex &rhs)
57{
58 const Real &lhsr = lhs.real();
59 const Real &lhsi = lhs.imag();
60 const Real &rhsr = rhs.real();
61 const Real &rhsi = rhs.imag();
62 return Complex(lhsr * rhsr - lhsi * rhsi, lhsi * rhsr + lhsr * rhsi);
63}
64}; // namespace eigen_mpfr
65#endif
66
67namespace EigenM2 {
68
69#ifdef NO_LAPACK
70// RR/CC
71
72// Need to rewrite matrix conversion functions
73
74void fill_to_MatrixXmp(const LMatrixRR& orig, MatrixXmpRR& result)
75{
76 for (int r=0; r<orig.numRows(); r++)
77 for (int c=0; c<orig.numColumns(); c++)
78 result(r,c) = orig.entry(r,c);
79}
80
81void fill_to_MatrixXmp(const LMatrixCC& orig, MatrixXmpCC& result)
82{
83 for (int r=0; r<orig.numRows(); r++)
84 for (int c=0; c<orig.numColumns(); c++)
85 //~ result(r,c) = Complex(Real(& orig.entry(r,c).re, false),Real(& orig.entry(r,c).im, false));
86 result(r,c) = std::complex<double>(orig.entry(r,c).re, orig.entry(r,c).im);
87}
88
89void fill_from_MatrixXmp(const MatrixXmpRR& orig, LMatrixRR& result)
90{
91 int numrows = orig.rows();
92 int numcols = orig.cols();
93 result.resize(numrows, numcols);
94 for (int r=0; r<numrows; r++)
95 for (int c=0; c<numcols; c++)
96 result.ring().set(result.entry(r,c), orig(r,c));
97}
98
99void fill_from_MatrixXmp(const MatrixXmpCC& orig, LMatrixCC& result)
100{
101 int numrows = orig.rows();
102 int numcols = orig.cols();
103 result.resize(numrows, numcols);
104 for (int r=0; r<numrows; r++)
105 for (int c=0; c<numcols; c++)
106 result.ring().set_from_doubles(result.entry(r,c),
107 orig(r,c).real(),
108 orig(r,c).imag());
109}
110
111bool SVD(const LMatrixRR *A,
112 LMatrixRR *Sigma,
113 LMatrixRR *U,
114 LMatrixRR *VT
115)
116{
117 // Create the correct matrices: A, Sigma, U, VT perhaps.
118 // call eigen
119 // Transform matrices back.
120
121 MatrixXmpRR AXmp(A->numRows(), A->numColumns());
122
123 fill_to_MatrixXmp(*A, AXmp);
124
125 Eigen::JacobiSVD<MatrixXmpRR> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
126
127 auto& eigenU = svd.matrixU();
128 auto& eigenVT = svd.matrixV().adjoint();
129 auto& eigenSigma = svd.singularValues();
130
131 fill_from_MatrixXmp(eigenU, *U);
132 fill_from_MatrixXmp(eigenVT, *VT);
133 fill_from_MatrixXmp(eigenSigma, *Sigma);
134
135 return true;
136}
137
138bool SVD(const LMatrixCC *A,
139 LMatrixRR *Sigma,
140 LMatrixCC *U,
141 LMatrixCC *VT
142)
143{
144 MatrixXmpCC AXmp(A->numRows(), A->numColumns());
145 fill_to_MatrixXmp(*A, AXmp);
146
147 Eigen::JacobiSVD<MatrixXmpCC> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
148
149 fill_from_MatrixXmp(svd.matrixU(), *U);
150 fill_from_MatrixXmp(svd.matrixV().adjoint(), *VT);
151 fill_from_MatrixXmp(svd.singularValues(), *Sigma);
152
153 return true;
154}
155
156bool SVD_divide_conquer(const LMatrixRR *A,
157 LMatrixRR *Sigma,
158 LMatrixRR *U,
159 LMatrixRR *VT
160)
161{
162 MatrixXmpRR AXmp(A->numRows(), A->numColumns());
163 fill_to_MatrixXmp(*A, AXmp);
164
165 Eigen::BDCSVD<MatrixXmpRR> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
166
167 fill_from_MatrixXmp(svd.matrixU(), *U);
168 fill_from_MatrixXmp(svd.matrixV().adjoint(), *VT);
169 fill_from_MatrixXmp(svd.singularValues(), *Sigma);
170
171 return true;
172}
173
174bool SVD_divide_conquer(const LMatrixCC *A,
175 LMatrixRR *Sigma,
176 LMatrixCC *U,
177 LMatrixCC *VT
178)
179{
180 MatrixXmpCC AXmp(A->numRows(), A->numColumns());
181 fill_to_MatrixXmp(*A, AXmp);
182
183 Eigen::BDCSVD<MatrixXmpCC> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
184
185 fill_from_MatrixXmp(svd.matrixU(), *U);
186 fill_from_MatrixXmp(svd.matrixV().adjoint(), *VT);
187 fill_from_MatrixXmp(svd.singularValues(), *Sigma);
188
189 return true;
190}
191
192bool eigenvalues(const LMatrixRR *A, LMatrixCC *eigenvals) {
193 MatrixXmpRR AXmp(A->numRows(), A->numColumns());
194 fill_to_MatrixXmp(*A, AXmp);
195
196 Eigen::EigenSolver<MatrixXmpRR> es(AXmp,false/*no eigenvectors*/);
197 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
198
199 return true;
200}
201
202bool eigenvalues(const LMatrixCC *A, LMatrixCC *eigenvals) {
203 MatrixXmpCC AXmp(A->numRows(), A->numColumns());
204 fill_to_MatrixXmp(*A, AXmp);
205
206 Eigen::ComplexEigenSolver<MatrixXmpCC> ces(AXmp, false);
207 fill_from_MatrixXmp(ces.eigenvalues(), *eigenvals);
208
209 return true;
210}
211
212bool eigenvalues_hermitian(const LMatrixRR *A, LMatrixRR *eigenvals) {
213 MatrixXmpRR AXmp(A->numRows(), A->numColumns());
214 fill_to_MatrixXmp(*A, AXmp);
215
216 Eigen::SelfAdjointEigenSolver<MatrixXmpRR> es(AXmp, false);
217 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
218
219 return true;
220}
221
222bool eigenvalues_hermitian(const LMatrixCC *A, LMatrixRR *eigenvals) {
223 MatrixXmpCC AXmp(A->numRows(), A->numColumns());
224 fill_to_MatrixXmp(*A, AXmp);
225
226 Eigen::SelfAdjointEigenSolver<MatrixXmpCC> es(AXmp, false);
227 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
228
229 return true;
230}
231
232bool eigenvectors(const LMatrixRR *A, LMatrixCC *eigenvals, LMatrixCC *eigenvecs) {
233 MatrixXmpRR AXmp(A->numRows(), A->numColumns());
234 fill_to_MatrixXmp(*A, AXmp);
235
236 Eigen::EigenSolver<MatrixXmpRR> es(AXmp);
237 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
238 fill_from_MatrixXmp(es.eigenvectors(), *eigenvecs);
239
240 return true;
241}
242
243bool eigenvectors(const LMatrixCC *A, LMatrixCC *eigenvals, LMatrixCC *eigenvecs) {
244 MatrixXmpCC AXmp(A->numRows(), A->numColumns());
245 fill_to_MatrixXmp(*A, AXmp);
246
247 Eigen::ComplexEigenSolver<MatrixXmpCC> ces(AXmp);
248 fill_from_MatrixXmp(ces.eigenvalues(), *eigenvals);
249 fill_from_MatrixXmp(ces.eigenvectors(), *eigenvecs);
250
251 return true;
252}
253
254bool eigenvectors_hermitian(const LMatrixRR *A, LMatrixRR *eigenvals, LMatrixRR *eigenvecs) {
255 MatrixXmpRR AXmp(A->numRows(), A->numColumns());
256 fill_to_MatrixXmp(*A, AXmp);
257
258 Eigen::SelfAdjointEigenSolver<MatrixXmpRR> es(AXmp);
259 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
260 fill_from_MatrixXmp(es.eigenvectors(), *eigenvecs);
261
262 return true;
263}
264
265bool eigenvectors_hermitian(const LMatrixCC *A, LMatrixRR *eigenvals, LMatrixCC *eigenvecs) {
266 MatrixXmpCC AXmp(A->numRows(), A->numColumns());
267 fill_to_MatrixXmp(*A, AXmp);
268
269 Eigen::SelfAdjointEigenSolver<MatrixXmpCC> es(AXmp);
270 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
271 fill_from_MatrixXmp(es.eigenvectors(), *eigenvecs);
272
273 return true;
274}
275
276bool least_squares(const LMatrixRR *A,
277 const LMatrixRR *B,
278 LMatrixRR *X
279)
280{
281 MatrixXmpRR AXmp(A->numRows(), A->numColumns());
282 fill_to_MatrixXmp(*A, AXmp);
283 MatrixXmpRR BXmp(B->numRows(), B->numColumns());
284 fill_to_MatrixXmp(*B, BXmp);
285
286 Eigen::BDCSVD<MatrixXmpRR> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
287
288 fill_from_MatrixXmp(svd.solve(BXmp), *X);
289
290 return true;
291}
292
293bool least_squares(const LMatrixCC *A,
294 const LMatrixCC *B,
295 LMatrixCC *X
296)
297{
298 MatrixXmpCC AXmp(A->numRows(), A->numColumns());
299 fill_to_MatrixXmp(*A, AXmp);
300 MatrixXmpCC BXmp(B->numRows(), B->numColumns());
301 fill_to_MatrixXmp(*B, BXmp);
302
303 Eigen::BDCSVD<MatrixXmpCC> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
304
305 fill_from_MatrixXmp(svd.solve(BXmp), *X);
306
307 return true;
308}
309#endif
310
311// RRR/CCC
312
314{
315 for (int r=0; r<orig.numRows(); r++)
316 for (int c=0; c<orig.numColumns(); c++)
317 result(r,c) = Real(& orig.entry(r,c), false);
318}
319
321{
322 for (int r=0; r<orig.numRows(); r++)
323 for (int c=0; c<orig.numColumns(); c++)
324 result(r,c) = Complex(Real(& orig.entry(r,c).re, false),Real(& orig.entry(r,c).im, false));
325}
326
328{
329 int numrows = orig.rows();
330 int numcols = orig.cols();
331 result.resize(numrows, numcols);
332 for (int r=0; r<numrows; r++)
333 for (int c=0; c<numcols; c++)
334 result.ring().set(result.entry(r,c), * orig(r,c).mpfr_srcptr());
335}
336
338{
339 int numrows = orig.rows();
340 int numcols = orig.cols();
341 result.resize(numrows, numcols);
342 for (int r=0; r<numrows; r++)
343 for (int c=0; c<numcols; c++)
344 result.ring().set_from_complex_mpfr(result.entry(r,c),
345 orig(r,c).real().mpfr_srcptr(),
346 orig(r,c).imag().mpfr_srcptr());
347}
348
349bool SVD(const LMatrixRRR *A,
350 LMatrixRRR *Sigma,
351 LMatrixRRR *U,
352 LMatrixRRR *VT
353)
354{
355 auto old_prec = Real::get_default_prec();
356 Real::set_default_prec(A->ring().get_precision());
357
358 MatrixXmpRRR AXmp(A->numRows(), A->numColumns());
359
360 fill_to_MatrixXmp(*A, AXmp);
361
362 Eigen::JacobiSVD<MatrixXmpRRR> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
363
364 auto& eigenU = svd.matrixU();
365 auto& eigenVT = svd.matrixV().adjoint();
366 auto& eigenSigma = svd.singularValues();
367
368 fill_from_MatrixXmp(eigenU, *U);
369 fill_from_MatrixXmp(eigenVT, *VT);
370 fill_from_MatrixXmp(eigenSigma, *Sigma);
371
372 Real::set_default_prec(old_prec);
373 return true;
374}
375
376bool SVD(const LMatrixCCC *A,
377 LMatrixRRR *Sigma,
378 LMatrixCCC *U,
379 LMatrixCCC *VT
380)
381{
382 auto old_prec = Real::get_default_prec();
383 Real::set_default_prec(A->ring().get_precision());
384
385 MatrixXmpCCC AXmp(A->numRows(), A->numColumns());
386 fill_to_MatrixXmp(*A, AXmp);
387
388 Eigen::JacobiSVD<MatrixXmpCCC> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
389
390 fill_from_MatrixXmp(svd.matrixU(), *U);
391 fill_from_MatrixXmp(svd.matrixV().adjoint(), *VT);
392 fill_from_MatrixXmp(svd.singularValues(), *Sigma);
393
394 Real::set_default_prec(old_prec);
395 return true;
396}
397
399 LMatrixRRR *Sigma,
400 LMatrixRRR *U,
401 LMatrixRRR *VT
402)
403{
404 auto old_prec = Real::get_default_prec();
405 Real::set_default_prec(A->ring().get_precision());
406
407 MatrixXmpRRR AXmp(A->numRows(), A->numColumns());
408 fill_to_MatrixXmp(*A, AXmp);
409
410 Eigen::BDCSVD<MatrixXmpRRR> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
411
412 fill_from_MatrixXmp(svd.matrixU(), *U);
413 fill_from_MatrixXmp(svd.matrixV().adjoint(), *VT);
414 fill_from_MatrixXmp(svd.singularValues(), *Sigma);
415
416 Real::set_default_prec(old_prec);
417 return true;
418}
419
421 LMatrixRRR *Sigma,
422 LMatrixCCC *U,
423 LMatrixCCC *VT
424)
425{
426 auto old_prec = Real::get_default_prec();
427 Real::set_default_prec(A->ring().get_precision());
428
429 MatrixXmpCCC AXmp(A->numRows(), A->numColumns());
430 fill_to_MatrixXmp(*A, AXmp);
431
432 Eigen::BDCSVD<MatrixXmpCCC> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
433
434 fill_from_MatrixXmp(svd.matrixU(), *U);
435 fill_from_MatrixXmp(svd.matrixV().adjoint(), *VT);
436 fill_from_MatrixXmp(svd.singularValues(), *Sigma);
437
438 Real::set_default_prec(old_prec);
439 return true;
440}
441
442bool eigenvalues(const LMatrixRRR *A, LMatrixCCC *eigenvals) {
443 auto old_prec = Real::get_default_prec();
444 Real::set_default_prec(A->ring().get_precision());
445
446 MatrixXmpRRR AXmp(A->numRows(), A->numColumns());
447 fill_to_MatrixXmp(*A, AXmp);
448
449 Eigen::EigenSolver<MatrixXmpRRR> es(AXmp,false);
450 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
451
452 Real::set_default_prec(old_prec);
453 return true;
454}
455
456bool eigenvalues(const LMatrixCCC *A, LMatrixCCC *eigenvals) {
457 auto old_prec = Real::get_default_prec();
458 Real::set_default_prec(A->ring().get_precision());
459
460 MatrixXmpCCC AXmp(A->numRows(), A->numColumns());
461 fill_to_MatrixXmp(*A, AXmp);
462
463 Eigen::ComplexEigenSolver<MatrixXmpCCC> ces(AXmp, false);
464 fill_from_MatrixXmp(ces.eigenvalues(), *eigenvals);
465
466 Real::set_default_prec(old_prec);
467 return true;
468}
469
470bool eigenvalues_hermitian(const LMatrixRRR *A, LMatrixRRR *eigenvals) {
471 auto old_prec = Real::get_default_prec();
472 Real::set_default_prec(A->ring().get_precision());
473
474 MatrixXmpRRR AXmp(A->numRows(), A->numColumns());
475 fill_to_MatrixXmp(*A, AXmp);
476
477 Eigen::SelfAdjointEigenSolver<MatrixXmpRRR> es(AXmp, false);
478 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
479
480 Real::set_default_prec(old_prec);
481 return true;
482}
483
484bool eigenvalues_hermitian(const LMatrixCCC *A, LMatrixRRR *eigenvals) {
485 auto old_prec = Real::get_default_prec();
486 Real::set_default_prec(A->ring().get_precision());
487
488 MatrixXmpCCC AXmp(A->numRows(), A->numColumns());
489 fill_to_MatrixXmp(*A, AXmp);
490
491 Eigen::SelfAdjointEigenSolver<MatrixXmpCCC> es(AXmp, false);
492 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
493
494 Real::set_default_prec(old_prec);
495 return true;
496}
497
498bool eigenvectors(const LMatrixRRR *A, LMatrixCCC *eigenvals, LMatrixCCC *eigenvecs) {
499 auto old_prec = Real::get_default_prec();
500 Real::set_default_prec(A->ring().get_precision());
501
502 MatrixXmpRRR AXmp(A->numRows(), A->numColumns());
503 fill_to_MatrixXmp(*A, AXmp);
504
505 Eigen::EigenSolver<MatrixXmpRRR> es(AXmp);
506 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
507 fill_from_MatrixXmp(es.eigenvectors(), *eigenvecs);
508
509 Real::set_default_prec(old_prec);
510 return true;
511}
512
513bool eigenvectors(const LMatrixCCC *A, LMatrixCCC *eigenvals, LMatrixCCC *eigenvecs) {
514 auto old_prec = Real::get_default_prec();
515 Real::set_default_prec(A->ring().get_precision());
516
517 MatrixXmpCCC AXmp(A->numRows(), A->numColumns());
518 fill_to_MatrixXmp(*A, AXmp);
519
520 Eigen::ComplexEigenSolver<MatrixXmpCCC> ces(AXmp);
521 fill_from_MatrixXmp(ces.eigenvalues(), *eigenvals);
522 fill_from_MatrixXmp(ces.eigenvectors(), *eigenvecs);
523
524 Real::set_default_prec(old_prec);
525 return true;
526}
527
528bool eigenvectors_hermitian(const LMatrixRRR *A, LMatrixRRR *eigenvals, LMatrixRRR *eigenvecs) {
529 auto old_prec = Real::get_default_prec();
530 Real::set_default_prec(A->ring().get_precision());
531
532 MatrixXmpRRR AXmp(A->numRows(), A->numColumns());
533 fill_to_MatrixXmp(*A, AXmp);
534
535 Eigen::SelfAdjointEigenSolver<MatrixXmpRRR> es(AXmp);
536 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
537 fill_from_MatrixXmp(es.eigenvectors(), *eigenvecs);
538
539 Real::set_default_prec(old_prec);
540 return true;
541}
542
543bool eigenvectors_hermitian(const LMatrixCCC *A, LMatrixRRR *eigenvals, LMatrixCCC *eigenvecs) {
544 auto old_prec = Real::get_default_prec();
545 Real::set_default_prec(A->ring().get_precision());
546
547 MatrixXmpCCC AXmp(A->numRows(), A->numColumns());
548 fill_to_MatrixXmp(*A, AXmp);
549
550 Eigen::SelfAdjointEigenSolver<MatrixXmpCCC> es(AXmp);
551 fill_from_MatrixXmp(es.eigenvalues(), *eigenvals);
552 fill_from_MatrixXmp(es.eigenvectors(), *eigenvecs);
553
554 Real::set_default_prec(old_prec);
555 return true;
556}
557
559 const LMatrixRRR *B,
560 LMatrixRRR *X
561)
562{
563 auto old_prec = Real::get_default_prec();
564 Real::set_default_prec(A->ring().get_precision());
565
566 MatrixXmpRRR AXmp(A->numRows(), A->numColumns());
567 fill_to_MatrixXmp(*A, AXmp);
568 MatrixXmpRRR BXmp(B->numRows(), B->numColumns());
569 fill_to_MatrixXmp(*B, BXmp);
570
571 Eigen::BDCSVD<MatrixXmpRRR> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
572
573 fill_from_MatrixXmp(svd.solve(BXmp), *X);
574
575 Real::set_default_prec(old_prec);
576 return true;
577}
578
580 const LMatrixCCC *B,
581 LMatrixCCC *X
582)
583{
584 auto old_prec = Real::get_default_prec();
585 Real::set_default_prec(A->ring().get_precision());
586
587 MatrixXmpCCC AXmp(A->numRows(), A->numColumns());
588 fill_to_MatrixXmp(*A, AXmp);
589 MatrixXmpCCC BXmp(B->numRows(), B->numColumns());
590 fill_to_MatrixXmp(*B, BXmp);
591
592 Eigen::BDCSVD<MatrixXmpCCC> svd(AXmp, Eigen::ComputeThinU | Eigen::ComputeThinV);
593
594 fill_from_MatrixXmp(svd.solve(BXmp), *X);
595
596 Real::set_default_prec(old_prec);
597 return true;
598}
599
600} // end of namespace EigenM2
601
602/*
603// Local Variables:
604// compile-command: "make -C $M2BUILDDIR/Macaulay2/e eigen.o "
605// indent-tabs-mode: nil
606// End:
607*/
size_t numRows() const
Definition dmat.hpp:144
ElementType & entry(size_t row, size_t column)
Definition dmat.hpp:148
const ACoeffRing & ring() const
Definition dmat.hpp:143
size_t numColumns() const
Definition dmat.hpp:145
unsigned long get_precision() const
Definition aring-CCC.hpp:88
unsigned long get_precision() const
Definition aring-RRR.hpp:82
std::complex< Real > Complex
Definition eigen.cpp:24
eigen_mpfr::mpreal Real
Definition eigen.cpp:23
Eigen::Matrix< Real, Eigen::Dynamic, Eigen::Dynamic > MatrixXmpRRR
Definition eigen.cpp:25
Eigen::Matrix< Complex, Eigen::Dynamic, Eigen::Dynamic > MatrixXmpCCC
Definition eigen.cpp:26
DMat< M2::ARingRRR > LMatrixRRR
Definition eigen.hpp:43
DMat< M2::ARingRR > LMatrixRR
Definition eigen.hpp:41
DMat< M2::ARingCC > LMatrixCC
Definition eigen.hpp:42
DMat< M2::ARingCCC > LMatrixCCC
Definition eigen.hpp:44
EigenM2 namespace — Eigen3-backed SVD / eigenvalues / eigenvectors / least-squares for DMat<R> over R...
VALGRIND_MAKE_MEM_DEFINED & result(result)
Vendored Holoborodko mpfr::mpreal C++ wrapper over MPFR.
void fill_to_MatrixXmp(const LMatrixRRR &orig, MatrixXmpRRR &result)
Definition eigen.cpp:313
bool SVD(const LMatrixRRR *A, LMatrixRRR *Sigma, LMatrixRRR *U, LMatrixRRR *VT)
Definition eigen.cpp:349
bool least_squares(const LMatrixRRR *A, const LMatrixRRR *B, LMatrixRRR *X)
Definition eigen.cpp:558
bool eigenvectors(const LMatrixRRR *A, LMatrixCCC *eigenvals, LMatrixCCC *eigenvecs)
Definition eigen.cpp:498
bool eigenvectors_hermitian(const LMatrixRRR *A, LMatrixRRR *eigenvals, LMatrixRRR *eigenvecs)
Definition eigen.cpp:528
bool SVD_divide_conquer(const LMatrixRRR *A, LMatrixRRR *Sigma, LMatrixRRR *U, LMatrixRRR *VT)
Definition eigen.cpp:398
bool eigenvalues(const LMatrixRRR *A, LMatrixCCC *eigenvals)
Definition eigen.cpp:442
void fill_from_MatrixXmp(const MatrixXmpRRR &orig, LMatrixRRR &result)
Definition eigen.cpp:327
bool eigenvalues_hermitian(const LMatrixRRR *A, LMatrixRRR *eigenvals)
Definition eigen.cpp:470
volatile int x
#define abs(x)
Definition polyroots.cpp:51
__mpfr_struct im
Definition ringelem.hpp:58
__mpfr_struct re
Definition ringelem.hpp:57