14411cf47Sjeremylt /// @file 252bfb9bbSJeremy L Thompson /// Test Symmetric Schur Decomposition 352bfb9bbSJeremy L Thompson /// \test Test Symmetric Schur Decomposition 4*f85e4a7bSJeremy L Thompson 5*f85e4a7bSJeremy L Thompson //TESTARGS(only="cpu") {ceed_resource} 657c64913Sjeremylt #include <ceed.h> 7673160d7Sjeremylt #include <ceed/backend.h> 8673160d7Sjeremylt #include <math.h> 949aac155SJeremy L Thompson #include <stdio.h> 1057c64913Sjeremylt 1157c64913Sjeremylt int main(int argc, char **argv) { 1257c64913Sjeremylt Ceed ceed; 134fee36f0SJeremy L Thompson CeedInt p = 4; 14673160d7Sjeremylt CeedScalar M[16], Q[16], lambda[4], Q_lambda_Qt[16]; 15673160d7Sjeremylt CeedBasis basis; 164fee36f0SJeremy L Thompson const CeedScalar *interpolation, *quadrature_weights; 1757c64913Sjeremylt 1857c64913Sjeremylt CeedInit(argv[1], &ceed); 19288c0443SJeremy L Thompson 20673160d7Sjeremylt // Create mass matrix 214fee36f0SJeremy L Thompson CeedBasisCreateTensorH1Lagrange(ceed, 1, 1, p, p, CEED_GAUSS, &basis); 224fee36f0SJeremy L Thompson CeedBasisGetInterp(basis, &interpolation); 234fee36f0SJeremy L Thompson CeedBasisGetQWeights(basis, &quadrature_weights); 244fee36f0SJeremy L Thompson for (int i = 0; i < p; i++) { 254fee36f0SJeremy L Thompson for (int j = 0; j < p; j++) { 26673160d7Sjeremylt CeedScalar sum = 0; 274fee36f0SJeremy L Thompson for (int k = 0; k < p; k++) sum += interpolation[p * k + i] * quadrature_weights[k] * interpolation[p * k + j]; 284fee36f0SJeremy L Thompson M[p * i + j] = sum; 294fee36f0SJeremy L Thompson Q[p * i + j] = sum; 3057c64913Sjeremylt } 312b730f8bSJeremy L Thompson } 32673160d7Sjeremylt 334fee36f0SJeremy L Thompson CeedSymmetricSchurDecomposition(ceed, Q, lambda, p); 34673160d7Sjeremylt 35673160d7Sjeremylt // Check diagonalization of M 364fee36f0SJeremy L Thompson for (int i = 0; i < p; i++) { 374fee36f0SJeremy L Thompson for (int j = 0; j < p; j++) { 38673160d7Sjeremylt CeedScalar sum = 0; 394fee36f0SJeremy L Thompson for (int k = 0; k < p; k++) sum += Q[p * i + k] * lambda[k] * Q[p * j + k]; 404fee36f0SJeremy L Thompson Q_lambda_Qt[p * i + j] = sum; 4152bfb9bbSJeremy L Thompson } 422b730f8bSJeremy L Thompson } 434fee36f0SJeremy L Thompson for (int i = 0; i < p; i++) { 444fee36f0SJeremy L Thompson for (int j = 0; j < p; j++) { 454fee36f0SJeremy L Thompson if (fabs(M[p * i + j] - Q_lambda_Qt[p * i + j]) > 100. * CEED_EPSILON) { 46673160d7Sjeremylt // LCOV_EXCL_START 474fee36f0SJeremy L Thompson printf("Error in diagonalization [%" CeedInt_FMT ", %" CeedInt_FMT "]: %f != %f\n", i, j, M[p * i + j], Q_lambda_Qt[p * i + j]); 48673160d7Sjeremylt // LCOV_EXCL_STOP 492b730f8bSJeremy L Thompson } 502b730f8bSJeremy L Thompson } 512b730f8bSJeremy L Thompson } 52673160d7Sjeremylt 53673160d7Sjeremylt CeedBasisDestroy(&basis); 5457c64913Sjeremylt CeedDestroy(&ceed); 5557c64913Sjeremylt return 0; 5657c64913Sjeremylt } 57