-
Notifications
You must be signed in to change notification settings - Fork 160
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Use SubMatrices to compute eigvals in demo qgbasinmodes #2402
Changes from all commits
4fd6596
d60c860
251e8a6
3d06769
92d65c1
6881416
ee296bb
80ec091
c31b7f9
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -109,6 +109,7 @@ Firedrake. We import the Firedrake, PETSc, and SLEPc libraries. :: | |
|
||
from firedrake import * | ||
from firedrake.petsc import PETSc | ||
import pyop2 | ||
try: | ||
from slepc4py import SLEPc | ||
except ImportError: | ||
|
@@ -154,13 +155,23 @@ We define the Test Function :math:`\phi` and the Trial Function | |
To build the weak formulation of our equation we need to build two PETSc | ||
matrices in the form of a generalized eigenvalue problem, | ||
:math:`A\psi = \lambda M\psi`. We impose the boundary conditions on the | ||
mass matrix :math:`M`, since that is where we used integration by parts. :: | ||
mass matrix :math:`M`, since that is where we used integration by parts. | ||
To avoid spurious eigenvalues associated with the rows of :math:`M` | ||
that are modified by the Dirichlet boundary conditions, we create | ||
submatrices that omit these rows and the correspoing columns. :: | ||
|
||
a = beta*phi*psi.dx(0)*dx | ||
m = -inner(grad(psi), grad(phi))*dx - F*psi*phi*dx | ||
petsc_a = assemble(a).M.handle | ||
petsc_m = assemble(m, bcs=bc).M.handle | ||
|
||
bcnodes = Vcg.dof_dset.lgmap.apply(bc.nodes).astype(pyop2.datatypes.IntType) | ||
ISbd = PETSc.IS().createGeneral(bcnodes, comm=petsc_a.comm) | ||
s, e = petsc_a.getOwnershipRange() | ||
ISin = ISbd.complement(s, e) | ||
A = petsc_a.createSubMatrix(ISin, ISin) | ||
M = petsc_m.createSubMatrix(ISin, ISin) | ||
APaganini marked this conversation as resolved.
Show resolved
Hide resolved
|
||
|
||
We can declare how many eigenpairs, eigenfunctions and eigenvalues, we | ||
want to find :: | ||
|
||
|
@@ -187,7 +198,7 @@ the PETSc parameters we previously declared. :: | |
|
||
es = SLEPc.EPS().create(comm=COMM_WORLD) | ||
es.setDimensions(num_eigenvalues) | ||
es.setOperators(petsc_a, petsc_m) | ||
es.setOperators(A, M) | ||
es.setFromOptions() | ||
es.solve() | ||
|
||
|
@@ -208,13 +219,13 @@ converge any eigenvalues at all. :: | |
If we did, we go ahead and extract them from the SLEPc eigenvalue | ||
solver:: | ||
|
||
vr, vi = petsc_a.getVecs() | ||
vr, vi = A.getVecs() | ||
|
||
lam = es.getEigenpair(0, vr, vi) | ||
|
||
and we gather the final eigenfunctions :: | ||
|
||
eigenmodes_real.vector()[:], eigenmodes_imag.vector()[:] = vr, vi | ||
eigenmodes_real.vector()[ISin.array], eigenmodes_imag.vector()[ISin.array] = vr, vi | ||
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. You should also insert the Dirichlet conditions into these eigenvectors ( There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. Is this necessary, given that |
||
|
||
We can now list and show plots for the eigenvalues and eigenfunctions | ||
that were found. :: | ||
|
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
In parallel,
ISbd.complement(s, e)
may rise exception:Maybe need add
to delete the ghost nodes and sort the array before creating the
ISbd
.