1 function simulation_data = lin_evol_opt_rb_simulation(model, reduced_data)
2 %
function simulation_data = lin_evol_opt_rb_simulation(model, reduced_data)
4 %
function, which performs a reduced basis online simulation
for
5 % the parameter vector mu, which is assumed to be set in the model
6 %
class, i.e. a previous model = model.set_mu(model,[...]) is assumed
9 % allowed dependency of data: Nmax, N, M, mu
10 % not allowed dependency of data: H
11 % allowed dependency of computation: Nmax, N, M, mu
12 % not allowed dependency of computation: H
13 % Unknown at
this stage: ---
15 % Required fields of model as required by the numerical operators and
16 % mu_names : the cell array of names of mu-components and
17 %
for each of these stringt, a corresponding
18 % field in model is expected.
19 % T : end-time of simulation
20 % nt : number of timesteps to compute
21 % error_norm :
'l2' or
'energy'
22 % L_I_inv_norm_bound: upper bound on implicit
operator inverse norm
23 % constant in time, a single scalar
24 % L_E_norm_bound: upper bounds on
explicit operator
25 % constant in time, a single scalar
26 % energy_norm_gamma: gamma >= 0 defining the weight in the energy norm
27 % coercivity_bound_name : name of the
function, which can
28 % computes a lower bound on the coercivity, e.g.
31 % plus fields required by coercivity_bound_name.m
33 % optional fields of model:
34 % data_const_in_time :
if this flag is set, then only operators
35 %
for first time instance are computed
36 % name_output_functional:
if this field is existent, then an
37 % output estimation is performed and error.estimtations
39 % generated fields of simulation_data:
40 % a: time sequence of solution coefficients, columns are
41 %
'a(:,k)' = `a^(k-1)`
42 % Delta:time sequence of `L^2`-posteriori error estimates
43 %
'Delta(k)' = `\Delta^{k-1}_N`
44 % or energy-norm-posterior error estimates
45 %
'Delta_energy(k)' = `\bar \Delta^{k-1}_N`
46 % depending on the field
"error_norm" in model.
48 %
if model.name_output_functional is set, then additionally, a
49 % sequence of output estimates
's(U(:,))' and error bound Delta_s is returned
51 % see the ***_gen_reduced_data() routine for specifications of the
52 % fields of reduced_data
54 % Markus Dihlmann 11.06.2010
57 printf('performing simulation for mu = %s', mat2str(get_mu(model)));
60 if (~isequal(model.error_norm,'l2')) && ...
61 (~isequal(model.error_norm,'energy'))
62 error('error_norm unknown!!');
65 %cgrid = grid_geometry(params);
66 nRB = length(reduced_data.a0{1});
67 a = zeros(nRB,model.nt+1); % matrix of RB-coefficients
68 Delta = zeros(1,model.nt+1); % vector of error estimators
69 model.dt = model.T/model.nt;
71 % initial data projection and linear combination
72 model.decomp_mode = 2;
73 sa0 = rb_init_values(model,[]);
74 a0 = lincomb_sequence(reduced_data.a0,sa0);
77 % loop over time steps: computation of a(t+1)==a^t
78 LL_I_is_speye = -1; % unknown state here
80 model.t = (t-1)*model.dt;
81 if model.verbose >= 20
82 disp([
'entered time-loop step ',num2str(t)]);
85 % linear combination of all quantities
86 % only once,
if data is
const in time
88 if (t==1) || (~model.data_const_in_time)
89 [sLL_I, sLL_E, sbb, sM_E, sM_b, sM_EE, sM_Eb, sM_bb, sM_I, sM_II, sM_IE, sM_Ib, ...
90 sM_EdEd, sM_IdId, sM_bdbd, sM_Ed, sM_Id, sM_bd, sM_IEd, sM_IId, sM_Ibd, sM_EEd, ...
91 sM_EId, sM_Ebd, sM_EdId, sM_Edbd, sM_Idbd] = rb_operators(model,[]);
92 LL_I = lincomb_sequence(reduced_data.LL_I,sLL_I);
93 LL_E = lincomb_sequence(reduced_data.LL_E,sLL_E);
94 bb = lincomb_sequence(reduced_data.bb,sbb);
95 M_E = lincomb_sequence(reduced_data.M_E,sM_E);
96 M_b = lincomb_sequence(reduced_data.M_b,sM_b);
97 M_EE = lincomb_sequence(reduced_data.M_EE,sM_EE);
98 M_Eb = lincomb_sequence(reduced_data.M_Eb,sM_Eb);
99 M_bb = lincomb_sequence(reduced_data.M_bb,sM_bb);
100 M_I = lincomb_sequence(reduced_data.M_I,sM_I);
101 M_II = lincomb_sequence(reduced_data.M_II,sM_II);
102 M_Ib = lincomb_sequence(reduced_data.M_Ib,sM_Ib);
103 M_IE = lincomb_sequence(reduced_data.M_IE,sM_IE);
104 if model.data_const_in_time
105 % inverse of implicit matrix! L_I
' = Id, L_E' = L_I^(-1) *
106 % L_E, bb = L_I^(-1) bb
110 LL_I = speye(size(LL_I));
112 elseif isequal(LL_I, speye(size(LL_I)))
117 % solve LL_I* a(:,t+1) = LL_E * a(:,t) + bb
118 rhs = LL_E * a(:,t) + bb;
119 % warning('this does not work for pure space operators (independent of delta t). In that case use the commented line below.');
120 %rhs = a(:,t) + model.dt * (LL_E * a(:,t) + bb);
121 % check whether pure explicit problem:
122 if (LL_I_is_speye == 1)
123 a(:,t+1) = a(:,t)+model.dt*rhs;
124 elseif (LL_I_is_speye == -1) && (max(max(LL_I-speye(size(LL_I))))<1.0e-3)
125 a(:,t+1) = a(:,t)+model.dt*rhs;
126 else % solve linear system
127 % disp('check symmetry and choose solver accordingly!');
129 % nonsymmetric solvers:
130 % [U(:,t+1), flag] = bicgstab(Li,rhs,[],1000);
131 % [U(:,t+1), flag] = cgs(Li,rhs,[],1000);
132 % symmetric solver, non pd:
133 % see bug_symmlq for a very strange bug: cannot solve identity system!
134 % [U(:,t+1), flag] = symmlq(Li,rhs,[],1000);
135 % [U(:,t+1), flag] = minres(Li,rhs,[],1000);
136 % symmetric solver, pd:
137 % [a(:,t+1), flag] = pcg(LL_I,rhs,[],1000);
138 [a(:,t+1), flag] = bicgstab(LL_I,rhs,[],1000);
140 disp(['error in system solution, solver return flag = ', ...
146 % compute error estimate recursively
150 res_norm_times_dt_sqr = a(:,t+1)'*a(:,t+1) - 2*a(:,t+1)' * a(:,t) + a(:,t)'*a(:,t) ...
151 +2*model.dt*( a(:,t)'*M_E*a(:,t) - a(:,t)'*M_E*a(:,t+1) ...
152 +M_b*a(:,t) - M_b*a(:,t+1) ...
153 +a(:,t+1)'*M_I*a(:,t) - a(:,t+1)'*M_I*a(:,t+1)) ...
154 +((model.dt)^2)* ( a(:,t)'*M_EE*a(:,t) + a(:,t+1)'*M_II*a(:,t+1) + M_bb ...
155 +2*( a(:,t+1)'*M_IE*a(:,t) +a(:,t)'*M_Eb + a(:,t+1)'*M_Ib));
157 % ensure real estimators (could be complex due to numerics)
158 if res_norm_times_dt_sqr>=0
159 res_norm_times_dt = sqrt(res_norm_times_dt_sqr);
161 res_norm_times_dt = 0;
164 if isequal(model.error_norm,'l2')
165 Delta(t+1) = res_norm_times_dt + model.L_E_norm_bound * Delta(t);
167 % only sum up the squares of the residuals, multiplication with coeff
168 % and squareroots are taken at the end.
169 disp('warning: error calculation not defined!!! See lin_evol_opt_rb_simulation line 161');
170 %Rkplus1sqr = max(res_norm_sqr/(params.dt.^2), 0);
171 %Delta(t+1) = Delta(t)+Rkplus1sqr;
175 if isequal(model.error_norm,'energy')
176 disp('warning: error calculation for energynorm not defined!!! See lin_evol_opt_rb_simulation line 168');
177 % now perform scaling and squareroot of energy-error-estimate:
178 %alpha = model.coercivity_bound_ptr(model);
179 %if max(model.L_E_norm_bound>1) || (alpha == 0)
180 % no reasonable estimation possible
183 % C = (sqrt(1-model.L_E_norm_bound.^2)+1) * 0.5;
184 % Coeff = model.dt /(4*alpha*C*(1-model.energy_norm_gamma * C));
185 % Delta = sqrt(Delta * Coeff);
189 % return simulation result
190 simulation_data = [];
191 simulation_data.a = a;
192 simulation_data.Delta = Delta;
193 simulation_data.LL_I = LL_I;
194 simulation_data.LL_E = LL_E;
196 if isfield(model,'name_output_functional')
197 if isequal(model.error_norm,'l2')
198 s = a' * reduced_data.s_RB;
199 if isfield(reduced_data,'s_l2norm')
200 Delta_s = reduced_data.s_l2norm * Delta;
201 simulation_data.Delta_s = Delta_s(:);
204 disp('warning: no L2_norm for output defined in lin_evol_opt_rb_simulation')
207 simulation_data.s = s(:);
210 error(['output estimation not implemented concerning energy-norm.' ...
211 ' choose l2 as error_norm!']);
function r = verbose(level, message, messageId)
This function displays messages depending on a message-id and/or a level. Aditionally you can set/res...