Fast assembly of time-dependent bilinear forms
Hello Everyone, I have an issue I have been struggling with for some time and I am unable to find a solution for it and I hope someone can help me with this. The issue is that I have a time dependent problem that results in the following weak form (already discretised in time): Find u^{n+1} \in V such that a_1(u^{n+1}, nu) + a_2(u^{n+1}, nu; w^{n+1/2)) = b(u^{n}), for all nu \in V - a_1 is a time-constant bilinear form, meaning that I can assemble it once for all time steps - a_2 is a time-dependent billinear form since it depends on w and this changes with the time step. My first approach was to assemble a_1 (using trial and test functions) in order to obtain a matrix. I could do this once, before the time stepping loop. Then, inside the time loop, I assembled a_2. As I tried to add the two resulting matrices I got an error stating addition is not possible for matrices. I then looked into LinearVariationalProblem and LinearVariationalSolver. My problem with this is that I am unable to understand if by defining the LinearVariational as the sum of a_1 and a_2, both will be kept constant or if only the a_2 part will be updated at each time step. So my question is: is there a standard way of solving this problem? Or do I need to recompute the whole system matrix for every time step (which is what I am doing now)? Thank you for your help. Kind regards, -artur palha
Dear Artur, Adding two matrices I think is not supported as, in general, those matrices can have different sparsity patterns, and adding two matrices of different sparsity patterns costs. As for your problem, I would simply assemble the entire a1 + a2 at every timestep. If: a1 = u*v*dx a2 = u*g(t)*v*dx where g(t) is the time dependent function, we have: a1+a2=u*(1+g(t))*v*dx so the cost of adding a1 to a2 is very small (just adding 1). To indicate that your matrix is not constant in time, you must set `constant_jacobian=False` when constructing the LinearVariationalProblem: https://www.firedrakeproject.org/firedrake.html#firedrake.variational_solver... Thanks, Koki ________________________________ From: firedrake-bounces@imperial.ac.uk <firedrake-bounces@imperial.ac.uk> on behalf of Artur Palha <artur.palha@gmail.com> Sent: Wednesday, January 20, 2021 4:17 PM To: firedrake <firedrake@imperial.ac.uk> Subject: [firedrake] Fast assembly of time-dependent bilinear forms Hello Everyone, I have an issue I have been struggling with for some time and I am unable to find a solution for it and I hope someone can help me with this. The issue is that I have a time dependent problem that results in the following weak form (already discretised in time): Find u^{n+1} \in V such that a_1(u^{n+1}, nu) + a_2(u^{n+1}, nu; w^{n+1/2)) = b(u^{n}), for all nu \in V - a_1 is a time-constant bilinear form, meaning that I can assemble it once for all time steps - a_2 is a time-dependent billinear form since it depends on w and this changes with the time step. My first approach was to assemble a_1 (using trial and test functions) in order to obtain a matrix. I could do this once, before the time stepping loop. Then, inside the time loop, I assembled a_2. As I tried to add the two resulting matrices I got an error stating addition is not possible for matrices. I then looked into LinearVariationalProblem and LinearVariationalSolver. My problem with this is that I am unable to understand if by defining the LinearVariational as the sum of a_1 and a_2, both will be kept constant or if only the a_2 part will be updated at each time step. So my question is: is there a standard way of solving this problem? Or do I need to recompute the whole system matrix for every time step (which is what I am doing now)? Thank you for your help. Kind regards, -artur palha
and t should be declared as Constant which can be updated using t.assign(<value>) to avoid recompilation. ________________________________ From: firedrake-bounces@imperial.ac.uk <firedrake-bounces@imperial.ac.uk> on behalf of Sagiyama, Koki <k.sagiyama@imperial.ac.uk> Sent: 21 January 2021 11:20 To: Artur Palha <artur.palha@gmail.com>; firedrake <firedrake@imperial.ac.uk> Subject: Re: [firedrake] Fast assembly of time-dependent bilinear forms Dear Artur, Adding two matrices I think is not supported as, in general, those matrices can have different sparsity patterns, and adding two matrices of different sparsity patterns costs. As for your problem, I would simply assemble the entire a1 + a2 at every timestep. If: a1 = u*v*dx a2 = u*g(t)*v*dx where g(t) is the time dependent function, we have: a1+a2=u*(1+g(t))*v*dx so the cost of adding a1 to a2 is very small (just adding 1). To indicate that your matrix is not constant in time, you must set `constant_jacobian=False` when constructing the LinearVariationalProblem: https://www.firedrakeproject.org/firedrake.html#firedrake.variational_solver... Thanks, Koki ________________________________ From: firedrake-bounces@imperial.ac.uk <firedrake-bounces@imperial.ac.uk> on behalf of Artur Palha <artur.palha@gmail.com> Sent: Wednesday, January 20, 2021 4:17 PM To: firedrake <firedrake@imperial.ac.uk> Subject: [firedrake] Fast assembly of time-dependent bilinear forms Hello Everyone, I have an issue I have been struggling with for some time and I am unable to find a solution for it and I hope someone can help me with this. The issue is that I have a time dependent problem that results in the following weak form (already discretised in time): Find u^{n+1} \in V such that a_1(u^{n+1}, nu) + a_2(u^{n+1}, nu; w^{n+1/2)) = b(u^{n}), for all nu \in V - a_1 is a time-constant bilinear form, meaning that I can assemble it once for all time steps - a_2 is a time-dependent billinear form since it depends on w and this changes with the time step. My first approach was to assemble a_1 (using trial and test functions) in order to obtain a matrix. I could do this once, before the time stepping loop. Then, inside the time loop, I assembled a_2. As I tried to add the two resulting matrices I got an error stating addition is not possible for matrices. I then looked into LinearVariationalProblem and LinearVariationalSolver. My problem with this is that I am unable to understand if by defining the LinearVariational as the sum of a_1 and a_2, both will be kept constant or if only the a_2 part will be updated at each time step. So my question is: is there a standard way of solving this problem? Or do I need to recompute the whole system matrix for every time step (which is what I am doing now)? Thank you for your help. Kind regards, -artur palha
Hi Koki and Colin, Thank you for your ideas. What you both propose is what I am currently doing: (i) assemble both together at each time step, and (ii) use time as constant and update it. So it seems that I am now doing the right thing. Thanks a lot for your help. -artur palha On Thu, Jan 21, 2021 at 12:47 PM Cotter, Colin J < colin.cotter@imperial.ac.uk> wrote:
and t should be declared as Constant which can be updated using t.assign(<value>) to avoid recompilation. ------------------------------ *From:* firedrake-bounces@imperial.ac.uk <firedrake-bounces@imperial.ac.uk> on behalf of Sagiyama, Koki <k.sagiyama@imperial.ac.uk> *Sent:* 21 January 2021 11:20 *To:* Artur Palha <artur.palha@gmail.com>; firedrake < firedrake@imperial.ac.uk> *Subject:* Re: [firedrake] Fast assembly of time-dependent bilinear forms
Dear Artur,
Adding two matrices I think is not supported as, in general, those matrices can have different sparsity patterns, and adding two matrices of different sparsity patterns costs.
As for your problem, I would simply assemble the entire a1 + a2 at every timestep. If: a1 = u*v*dx a2 = u*g(t)*v*dx where g(t) is the time dependent function, we have: a1+a2=u*(1+g(t))*v*dx so the cost of adding a1 to a2 is very small (just adding 1).
To indicate that your matrix is not constant in time, you must set `constant_jacobian=False` when constructing the LinearVariationalProblem:
https://www.firedrakeproject.org/firedrake.html#firedrake.variational_solver...
Thanks, Koki ------------------------------ *From:* firedrake-bounces@imperial.ac.uk <firedrake-bounces@imperial.ac.uk> on behalf of Artur Palha <artur.palha@gmail.com> *Sent:* Wednesday, January 20, 2021 4:17 PM *To:* firedrake <firedrake@imperial.ac.uk> *Subject:* [firedrake] Fast assembly of time-dependent bilinear forms
Hello Everyone,
I have an issue I have been struggling with for some time and I am unable to find a solution for it and I hope someone can help me with this.
The issue is that I have a time dependent problem that results in the following weak form (already discretised in time):
Find u^{n+1} \in V such that a_1(u^{n+1}, nu) + a_2(u^{n+1}, nu; w^{n+1/2)) = b(u^{n}), for all nu \in V
- a_1 is a time-constant bilinear form, meaning that I can assemble it once for all time steps - a_2 is a time-dependent billinear form since it depends on w and this changes with the time step.
My first approach was to assemble a_1 (using trial and test functions) in order to obtain a matrix. I could do this once, before the time stepping loop. Then, inside the time loop, I assembled a_2. As I tried to add the two resulting matrices I got an error stating addition is not possible for matrices.
I then looked into LinearVariationalProblem and LinearVariationalSolver. My problem with this is that I am unable to understand if by defining the LinearVariational as the sum of a_1 and a_2, both will be kept constant or if only the a_2 part will be updated at each time step.
So my question is: is there a standard way of solving this problem? Or do I need to recompute the whole system matrix for every time step (which is what I am doing now)?
Thank you for your help.
Kind regards,
-artur palha _______________________________________________ firedrake mailing list firedrake@imperial.ac.uk https://mailman.ic.ac.uk/mailman/listinfo/firedrake
participants (3)
- 
                
                Artur Palha
- 
                
                Cotter, Colin J
- 
                
                Sagiyama, Koki