Line |
Branch |
Exec |
Source |
1 |
|
|
// ______ ______ _ _ _____ ______ |
2 |
|
|
// | ____| ____| | (_)/ ____| | ____| |
3 |
|
|
// | |__ | |__ | | _| (___ ___| |__ |
4 |
|
|
// | __| | __| | | | |\___ \ / __| __| |
5 |
|
|
// | | | |____| |____| |____) | (__| |____ |
6 |
|
|
// |_| |______|______|_|_____/ \___|______| |
7 |
|
|
// Finite Elements for Life Sciences and Engineering |
8 |
|
|
// |
9 |
|
|
// License: LGL2.1 License |
10 |
|
|
// FELiScE default license: LICENSE in root folder |
11 |
|
|
// |
12 |
|
|
// Main authors: E. Schenone |
13 |
|
|
// |
14 |
|
|
|
15 |
|
|
// System includes |
16 |
|
|
|
17 |
|
|
// External includes |
18 |
|
|
|
19 |
|
|
// Project includes |
20 |
|
|
#include "Solver/eigenProblemALPCurv.hpp" |
21 |
|
|
#include "FiniteElement/elementMatrix.hpp" |
22 |
|
|
#include "FiniteElement/elementField.hpp" |
23 |
|
|
#include "Core/felisceParam.hpp" |
24 |
|
|
|
25 |
|
|
namespace felisce { |
26 |
|
|
/*! Construtor |
27 |
|
|
*/ |
28 |
|
✗ |
EigenProblemALPCurv::EigenProblemALPCurv(): |
29 |
|
✗ |
EigenProblemALP() |
30 |
|
|
{} |
31 |
|
|
|
32 |
|
✗ |
EigenProblemALPCurv::~EigenProblemALPCurv() |
33 |
|
|
= default; |
34 |
|
|
|
35 |
|
|
// Define Physical Variable associate to the problem |
36 |
|
✗ |
void EigenProblemALPCurv::initPerElementTypeBD() { |
37 |
|
✗ |
switch(m_problem) { |
38 |
|
✗ |
case 0: { |
39 |
|
|
//Init pointer on Finite Element, Variable or idVariable |
40 |
|
✗ |
m_ipotTransMemb = m_listVariable.getVariableIdList(potTransMemb); |
41 |
|
✗ |
m_fePotTransMembCurv = m_listCurvilinearFiniteElement[m_ipotTransMemb]; |
42 |
|
✗ |
m_elemFieldU0.initialize(DOF_FIELD,*m_fePotTransMembCurv); |
43 |
|
✗ |
break; |
44 |
|
|
} |
45 |
|
✗ |
case 1: { |
46 |
|
|
//Init pointer on Finite Element, Variable or idVariable |
47 |
|
✗ |
m_ipotTransMemb = m_listVariable.getVariableIdList(potTransMemb); |
48 |
|
✗ |
m_fePotTransMembCurv = m_listCurvilinearFiniteElement[m_ipotTransMemb]; |
49 |
|
✗ |
m_elemFieldU0.initialize(DOF_FIELD,*m_fePotTransMembCurv); |
50 |
|
✗ |
break; |
51 |
|
|
} |
52 |
|
✗ |
case 2: { |
53 |
|
|
//Init pointer on Finite Element, Variable or idVariable |
54 |
|
✗ |
m_ipotTransMemb = m_listVariable.getVariableIdList(potTransMemb); |
55 |
|
✗ |
m_fePotTransMembCurv = m_listCurvilinearFiniteElement[m_ipotTransMemb]; |
56 |
|
✗ |
m_elemFieldU0.initialize(DOF_FIELD,*m_fePotTransMembCurv); |
57 |
|
✗ |
break; |
58 |
|
|
} |
59 |
|
✗ |
default: |
60 |
|
✗ |
FEL_ERROR("Model not defined for ALP solver."); |
61 |
|
✗ |
break; |
62 |
|
|
} |
63 |
|
|
|
64 |
|
✗ |
if (FelisceParam::instance().hasInfarct) { |
65 |
|
✗ |
m_elemFieldFhNf0.initialize(DOF_FIELD,*m_fePotTransMembCurv); |
66 |
|
|
} |
67 |
|
|
} |
68 |
|
|
|
69 |
|
|
// Assemble Matrix |
70 |
|
✗ |
void EigenProblemALPCurv::computeElementArrayBD(const std::vector<Point*>& elemPoint, const std::vector<felInt>& elemIdPoint, felInt& iel) { |
71 |
|
|
IGNORE_UNUSED_ELEM_ID_POINT; |
72 |
|
|
|
73 |
|
✗ |
m_fePotTransMembCurv->updateMeasNormalContra(0, elemPoint); |
74 |
|
|
|
75 |
|
✗ |
switch(m_problem) { |
76 |
|
✗ |
case 0: { // FKPP |
77 |
|
|
// m_Matrix[0] = grad(phi_i) * grad(phi_j) |
78 |
|
✗ |
m_elementMatBD[m_idL]->grad_phi_i_grad_phi_j(1.,*m_fePotTransMembCurv,0,0,1); |
79 |
|
|
|
80 |
|
✗ |
if (FelisceParam::instance().hasInitialCondition) { |
81 |
|
|
// m_Matrix[0] += - m_coefChi * V * phi_i * phi_j |
82 |
|
✗ |
m_elemFieldU0.setValue(m_U_0_seq, *m_fePotTransMembCurv, iel, m_ipotTransMemb, m_ao, m_dof); |
83 |
|
✗ |
m_elementMatBD[m_idL]->a_phi_i_phi_j(- m_coefChi,m_elemFieldU0,*m_fePotTransMembCurv,0,0,1); |
84 |
|
|
} |
85 |
|
|
|
86 |
|
|
// Matrix[1] = phi_i * phi_j |
87 |
|
✗ |
m_elementMatBD[m_idG]->phi_i_phi_j(1.,*m_fePotTransMembCurv,0,0,1); |
88 |
|
|
|
89 |
|
✗ |
if (!FelisceParam::instance().solveEigenProblem) { |
90 |
|
✗ |
if (m_useImprovedRec) { |
91 |
|
|
// m_Matrix[m_numberOfMatrix-1] = grad(phi_i) * grad(phi_j) |
92 |
|
✗ |
m_elementMatBD[m_idK]->grad_phi_i_grad_phi_j(1.,*m_fePotTransMembCurv,0,0,1); |
93 |
|
|
} |
94 |
|
|
} |
95 |
|
✗ |
break; |
96 |
|
|
} |
97 |
|
✗ |
case 1: { // Monodomain |
98 |
|
|
// m_Matrix[0] = grad(phi_i) * grad(phi_j) |
99 |
|
✗ |
m_elementMatBD[m_idL]->grad_phi_i_grad_phi_j(FelisceParam::instance().intraTransvTensor,*m_fePotTransMembCurv,0,0,1); |
100 |
|
|
|
101 |
|
✗ |
if (FelisceParam::instance().testCase == 1) { |
102 |
|
✗ |
std::vector<double> elemFiber; |
103 |
|
✗ |
getFiberDirection(iel,m_ipotTransMemb, elemFiber); |
104 |
|
|
// m_Matrix[0] += (\sigma_i^l-\sigma_i^t) a vec a grad(phi_i) * grad(phi_j) |
105 |
|
✗ |
m_elementMatBD[m_idL]->tau_grad_phi_i_tau_grad_phi_j(FelisceParam::instance().intraFiberTensor-FelisceParam::instance().intraTransvTensor,elemFiber,*m_fePotTransMembCurv,0,0,1); |
106 |
|
|
} |
107 |
|
|
|
108 |
|
✗ |
if (FelisceParam::instance().hasInitialCondition) { |
109 |
|
|
// m_Matrix[0] += - m_coefChi * V * phi_i * phi_j |
110 |
|
✗ |
m_elemFieldU0.setValue(m_U_0_seq, *m_fePotTransMembCurv, iel, m_ipotTransMemb, m_ao, m_dof); |
111 |
|
✗ |
m_elementMatBD[m_idL]->a_phi_i_phi_j(- m_coefChi,m_elemFieldU0,*m_fePotTransMembCurv,0,0,1); |
112 |
|
|
} |
113 |
|
|
|
114 |
|
|
// m_Matrix[1] = phi_i * phi_j |
115 |
|
✗ |
m_elementMatBD[m_idG]->phi_i_phi_j(1.,*m_fePotTransMembCurv,0,0,1); |
116 |
|
|
|
117 |
|
✗ |
if (!FelisceParam::instance().solveEigenProblem) { |
118 |
|
|
|
119 |
|
✗ |
if (FelisceParam::instance().hasInfarct) { |
120 |
|
|
// m_Matrix[1] = B_ij = s(x) * phi_i * phi_j |
121 |
|
✗ |
m_elemFieldFhNf0.setValue(m_FhNf0, *m_fePotTransMembCurv, iel, m_ipotTransMemb, m_ao, m_dof); |
122 |
|
✗ |
m_elementMatBD[m_idGs]->a_phi_i_phi_j(1.,m_elemFieldFhNf0,*m_fePotTransMembCurv,0,0,1); |
123 |
|
|
} else { |
124 |
|
✗ |
double s = FelisceParam::instance().f0; |
125 |
|
|
// m_Matrix[1] = B_ij = s * phi_i * phi_j |
126 |
|
✗ |
m_elementMatBD[m_idGs]->phi_i_phi_j(s,*m_fePotTransMembCurv,0,0,1); |
127 |
|
|
} |
128 |
|
|
|
129 |
|
✗ |
if ( ( (m_tensorOrder == 4 ) & (m_useImprovedRec) ) || (m_tensorOrder == 3 ) ) { |
130 |
|
|
// m_Matrix[2] = E_ij = grad(phi_i) * grad(phi_j) |
131 |
|
✗ |
m_elementMatBD[m_idK]->grad_phi_i_grad_phi_j(FelisceParam::instance().intraTransvTensor,*m_fePotTransMembCurv,0,0,1); |
132 |
|
✗ |
if (FelisceParam::instance().testCase == 1) { |
133 |
|
✗ |
std::vector<double> elemFiber; |
134 |
|
✗ |
getFiberDirection(iel,m_ipotTransMemb, elemFiber); |
135 |
|
|
// m_Matrix[2] += (\sigma_i^l-\sigma_i^t) a vec a grad(phi_i) * grad(phi_j) |
136 |
|
✗ |
m_elementMatBD[m_idK]->tau_grad_phi_i_tau_grad_phi_j(FelisceParam::instance().intraFiberTensor-FelisceParam::instance().intraTransvTensor,elemFiber,*m_fePotTransMembCurv,0,0,1); |
137 |
|
|
} |
138 |
|
|
} |
139 |
|
|
|
140 |
|
✗ |
if (m_tensorOrder == 3 ) { |
141 |
|
✗ |
if (FelisceParam::instance().hasInfarct) { |
142 |
|
✗ |
if (FelisceParam::instance().testCase == 2) { |
143 |
|
|
// m_Matrix[3] = E^s_ij = s(x) * \sigma_i^t grad(phi_i), grad(phi_j) |
144 |
|
✗ |
m_elemFieldFhNf0.setValue(m_FhNf0, *m_fePotTransMembCurv, iel, m_ipotTransMemb, m_ao, m_dof); |
145 |
|
✗ |
m_elementMatBD[m_idKs]->a_grad_phi_i_grad_phi_j(FelisceParam::instance().intraTransvTensor,m_elemFieldFhNf0,*m_fePotTransMembCurv,0,0,1); |
146 |
|
✗ |
} else if (FelisceParam::instance().testCase == 1) { |
147 |
|
✗ |
FEL_ERROR("Error: infarct in fiber directed conductivity case not yet implemented."); |
148 |
|
|
} |
149 |
|
|
} else { |
150 |
|
✗ |
double s = FelisceParam::instance().f0; |
151 |
|
✗ |
if (FelisceParam::instance().testCase == 2) { |
152 |
|
|
// m_Matrix[3] = E^s_ij = s*\sigma_i^t grad(phi_i), grad(phi_j) |
153 |
|
✗ |
m_elementMatBD[m_idKs]->grad_phi_i_grad_phi_j(s*FelisceParam::instance().intraTransvTensor,*m_fePotTransMembCurv,0,0,1); |
154 |
|
✗ |
} else if (FelisceParam::instance().testCase == 1) { |
155 |
|
✗ |
std::vector<double> elemFiber; |
156 |
|
✗ |
getFiberDirection(iel,m_ipotTransMemb, elemFiber); |
157 |
|
|
// m_Matrix[3] = E^s_ij += s*(\sigma_i^l-\sigma_i^t) a vec a grad(phi_i) * grad(phi_j) |
158 |
|
✗ |
m_elementMatBD[m_idKs]->tau_grad_phi_i_tau_grad_phi_j(s*(FelisceParam::instance().intraFiberTensor-FelisceParam::instance().intraTransvTensor),elemFiber,*m_fePotTransMembCurv,0,0,1); |
159 |
|
|
} |
160 |
|
|
} |
161 |
|
|
} |
162 |
|
|
} |
163 |
|
✗ |
break; |
164 |
|
|
} |
165 |
|
✗ |
case 2: { |
166 |
|
|
|
167 |
|
|
// m_Matrix[0] = grad(phi_i) * grad(phi_j) |
168 |
|
✗ |
m_elementMatBD[m_idL]->grad_phi_i_grad_phi_j(FelisceParam::instance().intraTransvTensor,*m_fePotTransMembCurv,0,0,1); |
169 |
|
|
|
170 |
|
✗ |
if (FelisceParam::instance().testCase == 1) { |
171 |
|
✗ |
std::vector<double> elemFiber; |
172 |
|
✗ |
getFiberDirection(iel,m_ipotTransMemb, elemFiber); |
173 |
|
|
// m_Matrix[0] = \sigma_i^t \grad V_m |
174 |
|
✗ |
m_elementMatBD[m_idL]->grad_phi_i_grad_phi_j(FelisceParam::instance().intraTransvTensor,*m_fePotTransMembCurv,0,0,1); |
175 |
|
|
// m_Matrix[0] += (\sigma_i^l-\sigma_i^t) a vec a grad(phi_i) * grad(phi_j) |
176 |
|
✗ |
m_elementMatBD[m_idL]->tau_grad_phi_i_tau_grad_phi_j(FelisceParam::instance().intraFiberTensor-FelisceParam::instance().intraTransvTensor,elemFiber,*m_fePotTransMembCurv,0,0,1); |
177 |
|
|
} |
178 |
|
|
|
179 |
|
✗ |
if (FelisceParam::instance().hasInitialCondition) { |
180 |
|
|
// m_Matrix[0] += - m_coefChi * V * phi_i * phi_j |
181 |
|
✗ |
m_elemFieldU0.setValue(m_U_0_seq, *m_fePotTransMembCurv, iel, m_ipotTransMemb, m_ao, m_dof); |
182 |
|
✗ |
m_elementMatBD[m_idL]->a_phi_i_phi_j(- m_coefChi,m_elemFieldU0,*m_fePotTransMembCurv,0,0,1); |
183 |
|
|
} |
184 |
|
|
|
185 |
|
|
// m_Matrix[1] = phi_i * phi_j |
186 |
|
✗ |
m_elementMatBD[m_idG]->phi_i_phi_j(1.,*m_fePotTransMembCurv,0,0,1); |
187 |
|
|
|
188 |
|
✗ |
if (!FelisceParam::instance().solveEigenProblem) { |
189 |
|
✗ |
if (FelisceParam::instance().hasInfarct) { |
190 |
|
|
// m_Matrix[1] = B_ij = s(x) * phi_i * phi_j |
191 |
|
✗ |
m_elemFieldFhNf0.setValue(m_FhNf0, *m_fePotTransMembCurv, iel, m_ipotTransMemb, m_ao, m_dof); |
192 |
|
✗ |
m_elementMatBD[m_idGs]->a_phi_i_phi_j(1.,m_elemFieldFhNf0,*m_fePotTransMembCurv,0,0,1); |
193 |
|
|
} else { |
194 |
|
✗ |
double s = FelisceParam::instance().f0; |
195 |
|
|
// m_Matrix[1] = B_ij = s * phi_i * phi_j |
196 |
|
✗ |
m_elementMatBD[m_idGs]->phi_i_phi_j(s,*m_fePotTransMembCurv,0,0,1); |
197 |
|
|
} |
198 |
|
|
|
199 |
|
|
// Matrix[2] = E_ij = \sigma_i^t grad(phi_i), grad(phi_j) |
200 |
|
✗ |
m_elementMatBD[m_idK]->grad_phi_i_grad_phi_j(FelisceParam::instance().intraTransvTensor,*m_fePotTransMembCurv,0,0,1); |
201 |
|
|
// Matrix[3] = Q_ij = (\sigma_i^t+\sigma_e^t) grad(phi_i), grad(phi_j) |
202 |
|
✗ |
m_elementMatBD[m_idKie]->grad_phi_i_grad_phi_j(FelisceParam::instance().intraTransvTensor+FelisceParam::instance().extraTransvTensor,*m_fePotTransMembCurv,0,0,1); |
203 |
|
✗ |
if (FelisceParam::instance().testCase == 1) { |
204 |
|
✗ |
std::vector<double> elemFiber; |
205 |
|
✗ |
getFiberDirection(iel,m_ipotTransMemb, elemFiber); |
206 |
|
|
// Matrix[2] = Q_ij = (\sigma_i^t+\sigma_e^t) grad(phi_i), grad(phi_j) |
207 |
|
✗ |
m_elementMatBD[m_idKie]->grad_phi_i_grad_phi_j(FelisceParam::instance().intraTransvTensor+FelisceParam::instance().extraTransvTensor,*m_fePotTransMembCurv,0,0,1); |
208 |
|
|
// Matrix[3] = Q_ij += (\sigma_i^l-\sigma_i^t+\sigma_e^l-\sigma_e^t) a vec a grad(phi_i) * grad(phi_j) |
209 |
|
✗ |
m_elementMatBD[m_idKie]->tau_grad_phi_i_tau_grad_phi_j(FelisceParam::instance().intraFiberTensor-FelisceParam::instance().intraTransvTensor+FelisceParam::instance().extraFiberTensor-FelisceParam::instance().extraTransvTensor,elemFiber,*m_fePotTransMembCurv,0,0,1); |
210 |
|
|
} |
211 |
|
|
|
212 |
|
✗ |
if (m_tensorOrder == 3 ) { |
213 |
|
✗ |
if (FelisceParam::instance().hasInfarct) { |
214 |
|
✗ |
if (FelisceParam::instance().testCase == 2) { |
215 |
|
|
// m_Matrix[3] = E^s_ij = s(x) * \sigma_i^t grad(phi_i), grad(phi_j) |
216 |
|
✗ |
m_elemFieldFhNf0.setValue(m_FhNf0, *m_fePotTransMembCurv, iel, m_ipotTransMemb, m_ao, m_dof); |
217 |
|
✗ |
m_elementMatBD[m_idKs]->a_grad_phi_i_grad_phi_j(FelisceParam::instance().intraTransvTensor,m_elemFieldFhNf0,*m_fePotTransMembCurv,0,0,1); |
218 |
|
✗ |
} else if (FelisceParam::instance().testCase == 1) { |
219 |
|
✗ |
FEL_ERROR("Error: infarct in fiber directed conductivity case not yet implemented."); |
220 |
|
|
} |
221 |
|
|
} else { |
222 |
|
✗ |
double s = FelisceParam::instance().f0; |
223 |
|
✗ |
if (FelisceParam::instance().testCase == 2) { |
224 |
|
|
// m_Matrix[3] = E^s_ij = s*\sigma_i^t grad(phi_i), grad(phi_j) |
225 |
|
✗ |
m_elementMatBD[m_idKs]->grad_phi_i_grad_phi_j(s*FelisceParam::instance().intraTransvTensor,*m_fePotTransMembCurv,0,0,1); |
226 |
|
✗ |
} else if (FelisceParam::instance().testCase == 1) { |
227 |
|
✗ |
std::vector<double> elemFiber; |
228 |
|
✗ |
getFiberDirection(iel,m_ipotTransMemb, elemFiber); |
229 |
|
|
// m_Matrix[3] = E^s_ij += s*(\sigma_i^l-\sigma_i^t) a vec a grad(phi_i) * grad(phi_j) |
230 |
|
✗ |
m_elementMatBD[m_idKs]->tau_grad_phi_i_tau_grad_phi_j(s*(FelisceParam::instance().intraFiberTensor-FelisceParam::instance().intraTransvTensor),elemFiber,*m_fePotTransMembCurv,0,0,1); |
231 |
|
|
} |
232 |
|
|
} |
233 |
|
|
} |
234 |
|
|
} |
235 |
|
✗ |
break; |
236 |
|
|
} |
237 |
|
✗ |
default: |
238 |
|
✗ |
FEL_ERROR("Model not defined for ALP solver."); |
239 |
|
✗ |
break; |
240 |
|
|
} |
241 |
|
|
} |
242 |
|
|
|
243 |
|
|
} |
244 |
|
|
|