TestERowMatrix.cpp 15 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500
  1. /*
  2. * NICE-Core - efficient algebra and computer vision methods
  3. * - libbasicvector - A simple vector library
  4. * See file License for license information.
  5. */
  6. #ifdef NICE_USELIB_CPPUNIT
  7. #include <string>
  8. #include <iostream>
  9. #include <stdexcept>
  10. #include <cstddef>
  11. #include <core/basics/cppunitex.h>
  12. #include "core/vector/RowMatrixT.h"
  13. #include "core/vector/CheckedVectorT.h"
  14. #include "core/vector/CheckedRowMatrixT.h"
  15. #include "core/vector/Eigen.h"
  16. #include "core/vector/Algorithms.h"
  17. #include "TestERowMatrix.h"
  18. #ifdef NICE_USELIB_LINAL
  19. #include "LinAl/eigen.h"
  20. #endif
  21. CPPUNIT_TEST_SUITE_REGISTRATION( TestERowMatrix );
  22. using namespace NICE;
  23. using namespace std;
  24. void TestERowMatrix::setUp() {
  25. }
  26. void TestERowMatrix::tearDown() {
  27. }
  28. void TestERowMatrix::testAccess() {
  29. RowMatrixT<double> m(10, 7, 5.4);
  30. CPPUNIT_ASSERT_EQUAL(5.4, m(0, 3));
  31. CPPUNIT_ASSERT_EQUAL(5.4, m(9, 6));
  32. }
  33. void TestERowMatrix::testConst() {
  34. const char* data = "abcdef";
  35. RowMatrixT<char> v(data, 2, 3);
  36. CPPUNIT_ASSERT_EQUAL(2u, (uint)v.rows());
  37. CPPUNIT_ASSERT_EQUAL(3u, (uint)v.cols());
  38. for (unsigned int i = 0; i < v.rows(); i++) {
  39. for (unsigned int j = 0; j < v.cols(); j++) {
  40. // row major
  41. CPPUNIT_ASSERT_EQUAL(data[i*3+j], v(i, j));
  42. }
  43. }
  44. }
  45. void TestERowMatrix::testCopy() {
  46. const char data[] = "fkepw.xja8";
  47. unsigned int size = strlen(data);
  48. unsigned int rows = size / 2;
  49. unsigned int cols = 2;
  50. RowMatrixT<char> v(data, rows, cols);
  51. RowMatrixT<char> w(v);
  52. RowMatrixT<char> x(w);
  53. CPPUNIT_ASSERT_EQUAL(rows, (uint)v.rows());
  54. CPPUNIT_ASSERT_EQUAL(cols, (uint)v.cols());
  55. CPPUNIT_ASSERT_EQUAL(rows, (uint)w.rows());
  56. CPPUNIT_ASSERT_EQUAL(cols, (uint)w.cols());
  57. CPPUNIT_ASSERT_EQUAL(rows, (uint)x.rows());
  58. CPPUNIT_ASSERT_EQUAL(cols, (uint)x.cols());
  59. for (unsigned int i = 0; i < v.rows(); i++) {
  60. for (unsigned int j = 0; j < v.cols(); j++) {
  61. // row major
  62. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], v(i, j));
  63. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], w(i, j));
  64. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], x(i, j));
  65. }
  66. }
  67. }
  68. void TestERowMatrix::testExternal() {
  69. char data[] = "1234567890";
  70. unsigned int size = strlen(data);
  71. unsigned int rows = size / 5;
  72. unsigned int cols = 5;
  73. RowMatrixT<char> v(data, rows, cols, MatrixBase::external);
  74. data[5] = 'A';
  75. v(0, 3) = 'B';
  76. CPPUNIT_ASSERT_EQUAL(rows, (uint)v.rows());
  77. CPPUNIT_ASSERT_EQUAL(cols, (uint)v.cols());
  78. for (unsigned int i = 0; i < v.rows(); i++) {
  79. for (unsigned int j = 0; j < v.cols(); j++) {
  80. // row major
  81. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], v(i, j));
  82. }
  83. }
  84. // row major
  85. CPPUNIT_ASSERT_EQUAL('A', v(1, 0));
  86. CPPUNIT_ASSERT_EQUAL('B', data[3]);
  87. }
  88. void TestERowMatrix::testAssignment() {
  89. const char data[] = "fkepw.xja8";
  90. int size = strlen(data);
  91. unsigned int rows = size / 5;
  92. unsigned int cols = 5;
  93. RowMatrixT<char> a(data, rows, cols);
  94. std::auto_ptr<const RowMatrixT<char> >
  95. b(RowMatrixT<char>::createConst(data, rows, cols));
  96. RowMatrixT<char> t(a);
  97. RowMatrixT<char> u;
  98. u = a;
  99. RowMatrixT<char> v = a;
  100. RowMatrixT<char> w(*b);
  101. RowMatrixT<char> x;
  102. x = *b;
  103. RowMatrixT<char> y = *b;
  104. for (unsigned int i = 0; i < v.rows(); i++) {
  105. for (unsigned int j = 0; j < v.cols(); j++) {
  106. // row major
  107. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], t(i, j));
  108. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], u(i, j));
  109. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], v(i, j));
  110. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], w(i, j));
  111. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], x(i, j));
  112. CPPUNIT_ASSERT_EQUAL(data[i*cols+j], y(i, j));
  113. }
  114. }
  115. u = 'o';
  116. for (unsigned int i = 0; i < v.rows(); i++) {
  117. for (unsigned int j = 0; j < v.cols(); j++) {
  118. CPPUNIT_ASSERT_EQUAL('o', u(i, j));
  119. }
  120. }
  121. RowMatrixT<int> ev[3];
  122. ev[0]=RowMatrixT<int>(2, 2);
  123. ev[1]=RowMatrixT<int>(3, 3);
  124. ev[2]=RowMatrixT<int>(4, 4);
  125. RowMatrixT<RowMatrixT<int> > eev(ev,3,1);
  126. RowMatrixT<RowMatrixT<int> > copy_eev = eev;
  127. for (unsigned int i = 0; i < eev.rows(); i++) {
  128. for (unsigned int j = 0; j < eev.cols(); j++) {
  129. CPPUNIT_ASSERT_EQUAL(eev(i, j), copy_eev(i, j));
  130. }
  131. }
  132. }
  133. void TestERowMatrix::testArithmetics() {
  134. RowMatrixT<float> v(2, 10);
  135. for (unsigned int i = 0; i < v.rows(); i++) {
  136. for (unsigned int j = 0; j < v.cols(); j++) {
  137. v(i, j) = 100.0 - float(i+j);
  138. }
  139. }
  140. RowMatrixT<float> w(v);
  141. w *= 3.0;
  142. w -= v;
  143. for (unsigned int i = 0; i < v.rows(); i++) {
  144. for (unsigned int j = 0; j < v.cols(); j++) {
  145. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(2.0f * v(i, j), w(i, j), 1E-20);
  146. }
  147. }
  148. RowMatrixT<float> a(3, 1);
  149. RowMatrixT<float> b(3, 1);
  150. RowMatrixT<float> c(3, 1);
  151. for (unsigned int i = 0; i < a.rows(); i++) {
  152. a(i, 0) = float(i);
  153. b(i, 0) = float(i + 1);
  154. c(i, 0) = float(i + 2);
  155. }
  156. RowMatrixT<float> m(3, 1);
  157. m = 0.0f;
  158. m += a;
  159. m += b;
  160. m += c;
  161. m /= 3.0f;
  162. for (unsigned int i = 0; i < m.rows(); i++) {
  163. CPPUNIT_ASSERT_EQUAL(float(i + 1), m(i, 0));
  164. }
  165. }
  166. void TestERowMatrix::testRangeChecks() {
  167. CheckedRowMatrixT<double> v(10, 10, 4.5);
  168. CPPUNIT_ASSERT_EQUAL(4.5, v(0, 0));
  169. CPPUNIT_ASSERT_EQUAL(4.5, v(9, 9));
  170. CPPUNIT_ASSERT_THROW(v(-1, 0), std::out_of_range);
  171. CPPUNIT_ASSERT_THROW(v(0, -1), std::out_of_range);
  172. CPPUNIT_ASSERT_THROW(v(10, 0), std::out_of_range);
  173. CPPUNIT_ASSERT_THROW(v(0, 10), std::out_of_range);
  174. v(9, 9) = 5.1;
  175. CheckedRowMatrixT<double> w(v.getDataPointer(), v.rows(), v.cols());
  176. CPPUNIT_ASSERT_EQUAL(4.5, w(0, 0));
  177. CPPUNIT_ASSERT_EQUAL(5.1, w(9, 9));
  178. CPPUNIT_ASSERT_THROW(w(-1, 0), std::out_of_range);
  179. CPPUNIT_ASSERT_THROW(w(0, -1), std::out_of_range);
  180. CPPUNIT_ASSERT_THROW(w(10, 0), std::out_of_range);
  181. CPPUNIT_ASSERT_THROW(w(0, 10), std::out_of_range);
  182. }
  183. void TestERowMatrix::testEqual() {
  184. RowMatrixT<double> v(10, 10, 4.5);
  185. RowMatrixT<double> w(10, 10, 4.5);
  186. RowMatrixT<double> x(10, 10, 4.5);
  187. RowMatrixT<double> y(9, 10, 4.5);
  188. RowMatrixT<double> z;
  189. x(9,9)=4.7;
  190. CPPUNIT_ASSERT(z==z);
  191. CPPUNIT_ASSERT(!(z!=z));
  192. CPPUNIT_ASSERT(v==w);
  193. CPPUNIT_ASSERT(!(v!=w));
  194. CPPUNIT_ASSERT(v!=x);
  195. CPPUNIT_ASSERT(!(v==x));
  196. CPPUNIT_ASSERT_THROW(x==y, std::invalid_argument);
  197. CPPUNIT_ASSERT_THROW(x!=y, std::invalid_argument);
  198. }
  199. void TestERowMatrix::testTranspose() {
  200. {
  201. const float data[] = {13.0f,15.0f,17.0f,18.0f,1.0f,2.0f,3.0f,4.0f,5.0f};
  202. unsigned int rows = 3;
  203. unsigned int cols = 3;
  204. RowMatrixT<float> a(data, rows, cols);
  205. RowMatrixT<float> b(data, rows, cols);
  206. a.transposeInplace();
  207. for (unsigned int i = 0; i < a.rows(); i++) {
  208. for (unsigned int j = 0; j < a.cols(); j++) {
  209. CPPUNIT_ASSERT_EQUAL(a(i, j), b(j, i));
  210. }
  211. }
  212. RowMatrixT<float> c = a.transpose();
  213. CPPUNIT_ASSERT_EQUAL(a.rows(), c.cols());
  214. CPPUNIT_ASSERT_EQUAL(a.cols(), c.rows());
  215. for (unsigned int i = 0; i < a.rows(); i++) {
  216. for (unsigned int j = 0; j < a.cols(); j++) {
  217. CPPUNIT_ASSERT_EQUAL(a(i, j), c(j, i));
  218. }
  219. }
  220. //std::stringstream inout; inout << c << "!=" << a.transpose();
  221. //CPPUNIT_COND_STREAM(!(a==c), inout.str());
  222. RowMatrixT<float> d(data, 2, 3);
  223. RowMatrixT<float> e = d.transpose();
  224. CPPUNIT_ASSERT_EQUAL(d.rows(), e.cols());
  225. CPPUNIT_ASSERT_EQUAL(d.cols(), e.rows());
  226. for (unsigned int i = 0; i < d.rows(); i++) {
  227. for (unsigned int j = 0; j < d.cols(); j++) {
  228. CPPUNIT_ASSERT_EQUAL(d(i, j), e(j, i));
  229. }
  230. }
  231. }
  232. {
  233. const char data[] = "fkepw.xja";
  234. unsigned int rows = 3;
  235. unsigned int cols = 3;
  236. RowMatrixT<char> a(data, rows, cols);
  237. RowMatrixT<char> b(data, rows, cols);
  238. a.transposeInplace();
  239. for (unsigned int i = 0; i < a.rows(); i++) {
  240. for (unsigned int j = 0; j < a.cols(); j++) {
  241. CPPUNIT_ASSERT_EQUAL(a(i, j), b(j, i));
  242. }
  243. }
  244. RowMatrixT<char> c = a.transpose();
  245. CPPUNIT_ASSERT_EQUAL(a.rows(), c.cols());
  246. CPPUNIT_ASSERT_EQUAL(a.cols(), c.rows());
  247. for (unsigned int i = 0; i < a.rows(); i++) {
  248. for (unsigned int j = 0; j < a.cols(); j++) {
  249. CPPUNIT_ASSERT_EQUAL(a(i, j), c(j, i));
  250. }
  251. }
  252. //std::stringstream inout; inout << c << "!=" << a.transpose();
  253. //CPPUNIT_COND_STREAM(!(a==c), inout.str());
  254. RowMatrixT<char> d(data, 2, 3);
  255. RowMatrixT<char> e = d.transpose();
  256. CPPUNIT_ASSERT_EQUAL(d.rows(), e.cols());
  257. CPPUNIT_ASSERT_EQUAL(d.cols(), e.rows());
  258. for (unsigned int i = 0; i < d.rows(); i++) {
  259. for (unsigned int j = 0; j < d.cols(); j++) {
  260. CPPUNIT_ASSERT_EQUAL(d(i, j), e(j, i));
  261. }
  262. }
  263. }
  264. }
  265. void TestERowMatrix::testMultiply() {
  266. RowMatrixT<double> a(2,3);
  267. RowMatrixT<double> b(3,2);
  268. RowMatrixT<double> d(3,1);
  269. for (unsigned int i = 0; i < a.rows(); i++) {
  270. for (unsigned int j = 0; j < a.cols(); j++) {
  271. a(i, j) = i+j;
  272. }
  273. }
  274. for (unsigned int i = 0; i < b.rows(); i++) {
  275. for (unsigned int j = 0; j < b.cols(); j++) {
  276. b(i, j) = (int)i - (int)j;
  277. }
  278. }
  279. {
  280. RowMatrixT<double> m;
  281. CPPUNIT_ASSERT_THROW(m.multiply(d, a), Exception);
  282. }
  283. {
  284. RowMatrixT<double> m;
  285. CPPUNIT_ASSERT_THROW(m.multiply(a, d, true), Exception);
  286. }
  287. {
  288. RowMatrixT<double> m;
  289. CPPUNIT_ASSERT_THROW(m.multiply(b, d), Exception);
  290. }
  291. {
  292. RowMatrixT<double> m;
  293. CPPUNIT_ASSERT_THROW(m.multiply(d, b), Exception);
  294. }
  295. {
  296. RowMatrixT<double> m(2,1);
  297. CPPUNIT_ASSERT_NO_THROW(m.multiply(a, d));
  298. }
  299. {
  300. RowMatrixT<double> m(1,2);
  301. CPPUNIT_ASSERT_NO_THROW(m.multiply(d, a, true, true));
  302. }
  303. {
  304. RowMatrixT<double> m(1,2);
  305. CPPUNIT_ASSERT_NO_THROW(m.multiply(d, b, true, false));
  306. }
  307. {
  308. RowMatrixT<double> m(2,2);
  309. CPPUNIT_ASSERT_NO_THROW(m.multiply(a, a, false, true));
  310. }
  311. RowMatrixT<double> m;
  312. m.multiply(a, b);
  313. CPPUNIT_ASSERT_EQUAL(2u, (uint)m.cols());
  314. CPPUNIT_ASSERT_EQUAL(2u, (uint)m.rows());
  315. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(5.0, m(0, 0), 1E-20);
  316. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(2.0, m(0, 1), 1E-20);
  317. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(8.0, m(1, 0), 1E-20);
  318. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(2.0, m(1, 1), 1E-20);
  319. float array[]= {0.8385,0.6946,0.1730,0.1365,0.2844,0.5155
  320. ,0.5681,0.6213,0.9797,0.0118,0.4692,0.3340
  321. ,0.3704,0.7948,0.2714,0.8939,0.0648,0.4329
  322. ,0.7027,0.9568,0.2523,0.1991,0.9883,0.2259
  323. ,0.5466,0.5226,0.8757,0.2987,0.5828,0.5798
  324. ,0.4449,0.8801,0.7373,0.6614,0.4235,0.7604};
  325. RowMatrixT<float> c(array,6,6);
  326. c.transposeInplace();
  327. {
  328. RowMatrixT<float> m;
  329. m.multiply(c, c);
  330. double checksum=0;
  331. for(int i=0;i<6;i++)
  332. for(int j=0;j<6;j++) {
  333. checksum += m(i,j);
  334. checksum*=3.0;
  335. }
  336. std::stringstream inout; inout << checksum << endl << c << "*" << c << "=" << m;
  337. CPPUNIT_COND_STREAM(abs(checksum-3.72091e+17)/3.72091e+17<1e-6, inout.str());
  338. }
  339. {
  340. RowMatrixT<float> m;
  341. m.multiply(c, c, false, true);
  342. double checksum=0;
  343. for(int i=0;i<6;i++)
  344. for(int j=0;j<6;j++) {
  345. checksum += m(i,j);
  346. checksum*=3.0;
  347. }
  348. std::stringstream inout; inout << checksum << endl << c << "*" << c.transpose() << "=" << m;
  349. CPPUNIT_COND_STREAM(abs(checksum-4.92936e+17)/4.92936e+17<1e-6, inout.str());
  350. }
  351. {
  352. RowMatrixT<float> m;
  353. m.multiply(c, c, true, true);
  354. double checksum=0;
  355. for(int i=0;i<6;i++)
  356. for(int j=0;j<6;j++) {
  357. checksum += m(i,j);
  358. checksum*=3.0;
  359. }
  360. std::stringstream inout; inout << checksum << endl << c.transpose() << "*" << c.transpose() << "=" << m;
  361. CPPUNIT_COND_STREAM(abs(checksum-3.7386e+17)/3.7386e+17<1e-6, inout.str());
  362. }
  363. {
  364. RowMatrixT<float> m;
  365. m.multiply(c, c, true, false);
  366. double checksum=0;
  367. for(int i=0;i<6;i++)
  368. for(int j=0;j<6;j++) {
  369. checksum += m(i,j);
  370. checksum*=3.0;
  371. }
  372. std::stringstream inout; inout << checksum << endl << c.transpose() << "*" << c << " =" << m;
  373. CPPUNIT_COND_STREAM(abs(checksum-3.4161e+17)/3.4161e+17<1e-6, inout.str());
  374. }
  375. }
  376. void TestERowMatrix::testDet() {
  377. #ifdef NICE_USELIB_IPP
  378. RowMatrixT<float> a(20,20);
  379. a.setIdentity();
  380. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(1.0,det(a), 1E-6);
  381. RowMatrixT<float> b(20,20,0.0);
  382. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(0.0,det(b), 1E-6);
  383. float array[]= {0.8385,0.6946,0.1730,0.1365,0.2844,0.5155
  384. ,0.5681,0.6213,0.9797,0.0118,0.4692,0.3340
  385. ,0.3704,0.7948,0.2714,0.8939,0.0648,0.4329
  386. ,0.7027,0.9568,0.2523,0.1991,0.9883,0.2259
  387. ,0.5466,0.5226,0.8757,0.2987,0.5828,0.5798
  388. ,0.4449,0.8801,0.7373,0.6614,0.4235,0.7604};
  389. RowMatrixT<float> c(array,6,6);
  390. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(0.0498667,det(c), 1E-6);
  391. #endif
  392. }
  393. void TestERowMatrix::testEigenValues() {
  394. VectorT<float> buffer(3);
  395. RowMatrixT<float> b(3,3,0.0f);
  396. float data[][3]= {{1.00861, 2.17143, 2.90536},
  397. {9.01223, 2.17129, 1.90898},
  398. {8.01585, 2.17114, 9.9126},
  399. {7.01947, 2.171, 8.91622},
  400. {6.02309, 2.17086, 7.91984},
  401. {5.02671, 2.17071, 6.92346},
  402. {4.03033, 2.17057, 5.92708},
  403. {3.03396, 2.17042, 4.93071},
  404. {2.03758, 2.17028, 3.93433},
  405. {1.0412, 2.17013, 2.93795}};
  406. for(int i=0;i<10;i++) {
  407. //buffer = VectorT<float>::UniformRandom(3,1.0,10.0,i);
  408. buffer = VectorT<float>(data[i], 3, VectorBase::external);
  409. //std::cerr << buffer << std::endl;
  410. RowMatrixT<float> x(buffer.getDataPointer(),3,1,MatrixBase::external);
  411. RowMatrixT<float> a(3,3);
  412. a.multiply(x,x,false,true);
  413. b+=a;
  414. }
  415. RowMatrixT<double> evecs;
  416. VectorT<double> evals;
  417. RowMatrixT<double> I;
  418. #ifdef NICE_USELIB_IPP
  419. {
  420. float array[]= {11,4,14,4,-1,10,14,10,8};
  421. RowMatrixT<float> c(array,3,3);
  422. eigenvalues(c,&buffer);
  423. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(0.0,27-buffer(0), 2E-6);
  424. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(0.0,buffer(1), 2E-6);
  425. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(0.0,-9-buffer(2), 1E-6);
  426. }
  427. {
  428. eigenvalues(b,&buffer);
  429. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(677.0, buffer(0), 5);
  430. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(40.07, buffer(1), 3);
  431. // CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(674.32794189453, buffer(0), 1E-4);
  432. // CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(37.728626251220, buffer(1), 1E-4);
  433. double array[]= {292,101,295,104,48,122,295,122,384};
  434. RowMatrixT<double> c(array,3,3);
  435. eigenvectorvalues(c,evecs,evals);
  436. I.multiply(evecs,evecs.transpose());
  437. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(0.0, 1.0-det(I), 2E-15);
  438. }
  439. #endif
  440. #ifdef NICE_USELIB_LINAL
  441. {
  442. double array[]= {292,101,295,104,48,122,295,122,384};
  443. RowMatrixT<double> c(array,3,3);
  444. evals= VectorT<double>(3,0.0);
  445. evecs= RowMatrixT<double>(3,3,0.0);
  446. LinAl::MatrixCF<double> lc = c.linal();
  447. LinAl::VectorCC<double> levals = evals.linalCol();
  448. LinAl::MatrixCF<double> levecs = evecs.linal();
  449. eigensym(lc, levals, levecs, 3);
  450. // CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(674.32794189453, levals(0,0), 1E-4);
  451. // CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(37.728626251220, levals(1,0), 1E-4);
  452. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(677.0, levals(0,0), 5);
  453. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(40.07, levals(1,0), 1.1);
  454. I.multiply(evecs,evecs.transpose());
  455. double d = LinAl::det(I.linal());
  456. CPPUNIT_ASSERT_DOUBLES_EQUAL_NOT_NAN(0.0, 1.0-d, 1E-15);
  457. }
  458. #endif
  459. }
  460. #endif