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
Joint Inversions in SimPEG #797
Comments
Well, first of all, this is an epic issue @kimjaed Prof. @jiajiasun must be stocked to have you as a Master student. Looks like you have several interesting additions, and it will be easier for us all to bring it down in separate PRs (if possible). I'll take the first stab at this, but i am sure that @thast will have suggestions too when he gets back from vacation. You guys are working on the same problems. This is already possible, and called in our jargon a
The combo class will take care of differentiating each component and adding them |
All the Gauss-Newton math looks right, but under the hood, we never form these large systems. We just do matrix-vector products and add vectors at the end. |
I am pretty excited about the Sounds like you would like to create a new sub-class of Regularization, and you will need a directive to go along with it to update the model. This can be brought in on a single PR with a small example. I can help you with writing a small test that will just check for consistency of results. |
For the |
Will have to take a look, but I think the |
I agree this is a great criterion to stop. The |
Welcome to the SimPEG community @kimjaed! It looks like you have been busy 🚀 Would you be able to join us at the SimPEG meeting this week or next and give us an overview of your work? We hold the meetings every Tuesday at 2pm PDT: http://bit.ly/SimPEG2019. If that doesn't work with your schedule, just let us know and we can reschedule for one week. With all of the work you have done, a high-bandwidth conversation might be a good next step for getting your work included in SimPEG. |
@lheagy I sure can! I'll be joining and preparing some material to make it a bit clearer on what exactly I'm trying to achieve. |
Excellent @kimjaed! I look forward to seeing you tomorrow. The meetings are quite conversational: demos / walk throughs of notebooks or code are encouraged 😄 |
@fourndo I've actually looked into the
and I compute What I have now is that if I predefine the number of models we are inverting for
And same with the regularizations and second derivatives. I would loop over the number of models, compute the derivatives individually, and concatenate them. |
This is where SimPEG’s Each individual data misfit would take the full model, then the mapping would select which part of the model to use. |
Yep, @jcapriot is right. The mapping you need is called a Wire map. See the example here on how to use it: |
@kimjaed: for the meeting, here are the notes and the link to the zoom chat. I look forward to connecting!
|
Something that I forgot to ask, or maybe it wasn't clear to me.
Computing Edit: Do I have to access them by extracting the objfcts first?
|
You got it. So it's more general and you can have as many as you want. |
So I've been able to cut down my modifications to only a new |
Nice work @kimjaed! I have started pr #799 to break up the regularization into multiple files. @fourndo is willing to do a review and then we can merge that in and you can work from there. If you are comfortable working off of a branch, you can branch off of |
@kimjaed: we merged #799 and released SimPEG 0.11.6, so at this point, feel free to branch directly off of master and start a pr. You should have received an invite to the SimPEG organization on github, so you can do all of this directly in the SimPEG org. Please let me know if you didn't receive the invite and I can re-send it. If you run into any issues, just let us know and we can jump on to a quick call if that is helpful. I look forward to seeing your pr! 🎉 |
Most of these changes were brought in in version |
Hello,
My name is Jae Deok Kim and I am a Master's student working on Joint Inversions with Dr. Jiajia Sun at the University of Houston.
As far as I know, the joint inversions in SimPEG are inverting for different physical properties (e.g. electrical conductivity and volume) using a single dataset (https://docs.simpeg.xyz/content/examples/11-seis/seis_tomo_joint_with_volume.html).
We would like to add the functionalities for joint inversions that combine different physical properties (e.g. gravity and magnetics) from different datasets. This means that we would input multiple datasets of possibly different physical parameters (e.g. gravity and magnetics) and would output two different physical property models (e.g. density and susceptibility) that would be consistent in a predefined way (e.g. petrophysical relationships or structural similarity).
The joint inversion should be done within a single computational algorithm, with a single objective function and where all the models parameters are adjusted concurrently throughout the inversion.
Take for instance, the case of joint inversion of two models.
We define our objective function as:
The last term, , is the coupling term that mathematically defines the relationship between different model parameters.
The most prominent example would be the cross-gradient.
To minimize this objective function, we can still use the Gauss-Newton method by making some linear algebraic modifications.
Let me first restate the objective function in explicit form:
We can combine this so that, we work with a single vector that represents the stacked models:
Our goal then becomes to find
At each Gauss-Newton step, we solve the system of linear equations given by:
where,
More explicitly, the Hessian can be stated as:
And the gradient can be explicitly stated as:
By constructing the Hessian and gradient as shown, we are able to take advantage of the optimization code that is already in SimPEG to implement our joint inversions.
These are the modifications that I've done:
Coupling
: I've added aCoupling
class that stores the methods related to the specific coupling strategy we use for joint inversions. For now, I've only coded the cross-gradient method. The relevant functions arederiv
andderiv2
which compute the gradient and Hessian, respectively.For more detailed information on the cross-gradient, you may refer to this paper by Gallardo and Meju (2003) https://doi.org/10.1029/2003GL017370
Directives
: I've added aJointInversionDirective
class that inherits fromInversionDirective
, but we define some of the methods differently. Namely, for joint inversions we are now working with multiple data misfits, multiple regularizations, and a coupling term, so I've added methods that call and set the values for these objects.I've added a
SaveOutputEveryIteration_JointInversion
directive that will save the outputs of each iteration for joint inversions.I've added a
UpdatePreconditioner_JointInversion
directive that sets a Jacobi preconditioner for the joint inversion.Lastly, I've added a
Adaptive_Beta_Reweighting
directive that will adaptively change the trade-off parameters of the regularizations during the inversion. It makes sure that we stay within a certain range of our target data misfits.InvProblem
: I've created a newJointInvProblem
class that inherits fromBaseInvProblem
. The relevant function isevalFunction
, which computes the value of the objective function, as well as the gradient and Hessian (we store the Hessian as ascipy.sparse.linalg.LinearOperator
object).Optimization
: I would like to add another stopping criteria, which I've namedratio_x
, defined as .This captures information on how much we've updated the model, and if the update is negligibly small we decide we've converged. It's somewhat similar to the
moving_x
stopping criteria, but different in the sense that theratio_x
is like a percentage on the model update at each iteration, where asmoving_x
is relevant to the initial model.I've also added some
IterationPrinters
that are relevant for the joint inversion, such as printing multiple data misfits, multiple regularizations, the coupling term.Lastly, I've modified the
ProjectedGNCG
findsearchdirection
method, where I think it's more intuitive to use a for loopfor i in range(self.maxIterCG)
and have aif...then...break
statement inside the loop, instead of a while loop. For the convergence criteria of the Conjugate Gradient, I've found that usingr.dot(r) / self.g.dot(self.g) < self.tolCG
works better especially in cases where the residual does not easily fall below magnitudes of 1e-3.Inversion
: I've added aJointInversion
class that inherits fromBaseInversion
that simply sets theIterationPrinters
andStoppingCriteria
for the joint inversion.It's my first time contributing to an open-source project, so any guidance on how to proceed is appreciated (e.g. what tests I need to do?).
I'm opening this issue to discuss the possibility of adding these functionalities for joint inversions in SimPEG.
I've tested these modifications locally and the joint inversion runs successfully, so I'm ready to start a pull request any time, but first I'd like to hear back from the team.
Best regards,
Jae
The text was updated successfully, but these errors were encountered: