def test_2D(arpack_eigs, interface, x, num_evs, tol, atol, interactive=False): from fvm import JadaInterface from jadapy import jdqz numpy.random.seed(1234) jac_op = JadaInterface.JadaOp(interface.jacobian(x)) mass_op = JadaInterface.JadaOp(interface.mass_matrix()) alpha, beta = jdqz.jdqz(jac_op, mass_op, num_evs, tol=tol, subspace_dimensions=[20, 40], target=0.1) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x))) jdqz_eigs = jdqz_eigs[:num_evs] assert_allclose(jdqz_eigs.real, arpack_eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(arpack_eigs.imag), rtol=0, atol=atol) if not interactive: return x fig, ax = plt.subplots() ax.scatter(jdqz_eigs.real, jdqz_eigs.imag, marker='+') plt.show()
def test_Complex_Epetra(): try: from PyTrilinos import Epetra from jadapy import ComplexEpetraInterface except ImportError: pytest.skip("Trilinos not found") dtype = numpy.float64 numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 5 comm = Epetra.PyComm() map = Epetra.Map(n, 0, comm) a1, a2 = generate_Complex_Epetra_test_matrix(map, [n, n], dtype) b1, b2 = generate_Complex_Epetra_test_matrix(map, [n, n], dtype) interface = ComplexEpetraInterface.ComplexEpetraInterface(map) alpha, beta = jdqz.jdqz(a2, b2, k, tol=tol, interface=interface) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x))) eigs = scipy.linalg.eigvals(a1, b1) eigs = numpy.array(sorted(eigs, key=lambda x: abs(x))) eigs = eigs[:k] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol)
def test_jdqz_target_real(dtype): numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 6 a = generate_test_matrix([n, n], dtype) b = generate_test_matrix([n, n], dtype) target = 2 + 1j alpha, beta = jdqz.jdqz(a, b, k, target, tol=tol) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x - target))) eigs = scipy.linalg.eigvals(a, b) eigs = numpy.array(sorted(eigs, key=lambda x: abs(x - target))) eigs = eigs[:k] # In the real case, we store complex conjugate eigenpairs, so only # at least half of the eigenvalues are correct eigs = eigs[:k // 2] jdqz_eigs = jdqz_eigs[:k // 2] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol)
def test_jdqz_smallest_magnitude_eigenvectors(dtype): numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 5 a = generate_test_matrix([n, n], dtype) b = generate_test_matrix([n, n], dtype) alpha, beta, v = jdqz.jdqz(a, b, num=k, tol=tol, return_eigenvectors=True) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x))) jdqz_eigs = jdqz_eigs[:k] eigs = scipy.linalg.eigvals(a, b) eigs = numpy.array(sorted(eigs, key=lambda x: abs(x))) eigs = eigs[:k] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol) i = 0 while i < k: ctype = numpy.dtype(numpy.dtype(dtype).char.upper()) if dtype != ctype and alpha[i].imag: assert norm(beta[i].real * a @ v[:, i] - alpha[i].real * b @ v[:, i] + alpha[i].imag * b @ v[:, i + 1]) < atol assert norm(beta[i].real * a @ v[:, i + 1] - alpha[i].imag * b @ v[:, i] - alpha[i].real * b @ v[:, i + 1]) < atol i += 2 else: assert norm(beta[i] * a @ v[:, i] - alpha[i] * b @ v[:, i]) < atol i += 1
def test_prec_solve_2D(arpack_eigs, interface, x, num_evs, tol, atol, interactive=False): from fvm import JadaHYMLSInterface from jadapy import EpetraInterface from jadapy import jdqz numpy.random.seed(1234) jac_op = EpetraInterface.CrsMatrix(interface.jacobian(x)) mass_op = EpetraInterface.CrsMatrix(interface.mass_matrix()) jada_interface = JadaHYMLSInterface.JadaHYMLSInterface(interface.map, interface, preconditioned_solve=True) alpha, beta = jdqz.jdqz(jac_op, mass_op, num_evs, tol=tol, subspace_dimensions=[20, 40], interface=jada_interface) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x))) assert_allclose(jdqz_eigs.real, arpack_eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(arpack_eigs.imag), rtol=0, atol=atol) if not interactive: return x fig, ax = plt.subplots() ax.scatter(jdqz_eigs.real, jdqz_eigs.imag, marker='+') plt.show()
def test_jdqz_smallest_magnitude_initial_subspace(dtype): numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 5 a = generate_test_matrix([n, n], dtype) b = generate_test_matrix([n, n], dtype) alpha, beta, q, z = jdqz.jdqz(a, b, num=k, tol=tol, return_subspaces=True) alpha, beta = jdqz.jdqz(a, b, num=k, tol=tol, initial_subspaces=(q, z)) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x))) jdqz_eigs = jdqz_eigs[:k] eigs = scipy.linalg.eigvals(a, b) eigs = numpy.array(sorted(eigs, key=lambda x: abs(x))) eigs = eigs[:k] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol)
def test_Epetra_eigenvectors(): try: from PyTrilinos import Epetra from jadapy import EpetraInterface except ImportError: pytest.skip("Trilinos not found") dtype = numpy.float64 numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 5 comm = Epetra.PyComm() map = Epetra.Map(n, 0, comm) a1, a2 = generate_Epetra_test_matrix(map, [n, n], dtype) b1, b2 = generate_Epetra_test_matrix(map, [n, n], dtype) interface = EpetraInterface.EpetraInterface(map) alpha, beta, v = jdqz.jdqz(a2, b2, num=k, tol=tol, return_eigenvectors=True, interface=interface) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x))) jdqz_eigs = jdqz_eigs[:k] eigs = scipy.linalg.eigvals(a1, b1) eigs = numpy.array(sorted(eigs, key=lambda x: abs(x))) eigs = eigs[:k] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol) i = 0 while i < k: if alpha[i].imag: assert norm(a2 @ v[:, i] * beta[i].real - b2 @ v[:, i] * alpha[i].real + b2 @ v[:, i + 1] * alpha[i].imag) < atol assert norm(a2 @ v[:, i + 1] * beta[i].real - b2 @ v[:, i] * alpha[i].imag - b2 @ v[:, i + 1] * alpha[i].real) < atol i += 2 else: assert norm(a2 @ v[:, i] * beta[i].real - b2 @ v[:, i] * alpha[i].real) < atol i += 1
def eigs(self, state, return_eigenvectors=False): '''Compute the generalized eigenvalues of beta * J(x) * v = alpha * M * v.''' from jadapy import jdqz, Target from fvm.JadaInterface import JadaOp, JadaInterface jac_op = JadaOp(self.jacobian(state)) mass_op = JadaOp(self.mass_matrix()) jada_interface = JadaInterface(self, jac_op, mass_op, jac_op.shape[0], numpy.complex128) parameters = self.parameters.get('Eigenvalue Solver', {}) target = parameters.get('Target', Target.LargestRealPart) subspace_dimensions = [ parameters.get('Minimum Subspace Dimension', 30), parameters.get('Maximum Subspace Dimension', 60) ] tol = parameters.get('Tolerance', 1e-7) num = parameters.get('Number of Eigenvalues', 5) result = jdqz.jdqz(jac_op, mass_op, num, tol=tol, subspace_dimensions=subspace_dimensions, target=target, interface=jada_interface, arithmetic='complex', prec=jada_interface.shifted_prec, return_eigenvectors=return_eigenvectors, return_subspaces=True, initial_subspaces=self._subspaces) if return_eigenvectors: alpha, beta, v, q, z = result self._subspaces = [q, z] idx = range(len(alpha)) idx = sorted(idx, key=lambda i: -(alpha[i] / beta[i]).real) w = v.copy() eigs = alpha.copy() for i in range(len(idx)): w[:, i] = v[:, idx[i]] eigs[i] = alpha[idx[i]] / beta[idx[i]] return eigs, w else: alpha, beta, q, z = result self._subspaces = [q, z] return numpy.array(sorted(alpha / beta, key=lambda x: -x.real))
def test_complex_shifted_prec_solve_2D(arpack_eigs, interface, x, num_evs, tol, atol, interactive=False): from fvm import JadaInterface from jadapy import jdqz numpy.random.seed(1234) jac_op = JadaInterface.JadaOp(interface.jacobian(x)) mass_op = JadaInterface.JadaOp(interface.mass_matrix()) jada_interface = JadaInterface.JadaInterface(interface, jac_op, mass_op, len(x), numpy.complex128, preconditioned_solve=True, shifted=True) assert jada_interface.preconditioned_solve assert jada_interface.shifted alpha, beta, v = jdqz.jdqz(jac_op, mass_op, num_evs, tol=tol, subspace_dimensions=[20, 40], arithmetic='complex', return_eigenvectors=True, interface=jada_interface) check_eigenvalues(jac_op, mass_op, alpha / beta, v, num_evs, atol) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x))) assert_allclose(jdqz_eigs.real, arpack_eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(arpack_eigs.imag), rtol=0, atol=atol) if not interactive: return x fig, ax = plt.subplots() ax.scatter(jdqz_eigs.real, jdqz_eigs.imag, marker='+') plt.show()
def test_jdqz_largest_real(dtype): numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 5 a = generate_test_matrix([n, n], dtype) b = generate_test_matrix([n, n], dtype) alpha, beta = jdqz.jdqz(a, b, k, Target.LargestRealPart, tol=tol) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: -x.real)) eigs = scipy.linalg.eigvals(a, b) eigs = numpy.array(sorted(eigs, key=lambda x: -x.real)) eigs = eigs[:k] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol)
def test_jdqz_petrov(dtype): numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 5 a = generate_test_matrix([n, n], dtype) b = generate_test_matrix([n, n], dtype) alpha, beta = jdqz.jdqz(a, b, num=k, tol=tol, testspace='Petrov') jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x))) eigs = scipy.linalg.eigvals(a, b) eigs = numpy.array(sorted(eigs, key=lambda x: abs(x))) eigs = eigs[:k] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol)
def test_jdqz_target(dtype): numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 5 a = generate_test_matrix([n, n], dtype) b = generate_test_matrix([n, n], dtype) target = 2 + 1j alpha, beta = jdqz.jdqz(a, b, k, target, tol=tol, arithmetic='complex') jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x - target))) eigs = scipy.linalg.eigvals(a, b) eigs = numpy.array(sorted(eigs, key=lambda x: abs(x - target))) eigs = eigs[:k] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol)
def test_jdqz_largest_magnitude_lowdim(dtype): numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 2 a = generate_test_matrix([n, n], dtype) b = generate_test_matrix([n, n], dtype) alpha, beta = jdqz.jdqz(a, b, k, Target.LargestMagnitude, tol=tol, subspace_dimensions=[6, 16]) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: -abs(x))) eigs = scipy.linalg.eigvals(a, b) eigs = numpy.array(sorted(eigs, key=lambda x: -abs(x))) eigs = eigs[:k] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol)
def test_jdqz_prec(dtype): numpy.random.seed(1234) tol = numpy.finfo(dtype).eps * 1e3 atol = tol * 10 n = 20 k = 5 a = generate_test_matrix([n, n], dtype) b = generate_test_matrix([n, n], dtype) inv = scipy.sparse.linalg.spilu(scipy.sparse.csc_matrix(a)) def _prec(x, *args): return inv.solve(x) alpha, beta = jdqz.jdqz(a, b, num=k, tol=tol, prec=_prec) jdqz_eigs = numpy.array(sorted(alpha / beta, key=lambda x: abs(x))) eigs = scipy.linalg.eigvals(a, b) eigs = numpy.array(sorted(eigs, key=lambda x: abs(x))) eigs = eigs[:k] assert_allclose(jdqz_eigs.real, eigs.real, rtol=0, atol=atol) assert_allclose(abs(jdqz_eigs.imag), abs(eigs.imag), rtol=0, atol=atol)