5 #include "../../../toolkits/toolkits.h"
6 #include "../../../classes/classes.h"
7 #include "../../../shared/shared.h"
8 #include "../../MeshPartitionx/MeshPartitionx.h"
9 #include "../ModelProcessorx.h"
13 bool control_analysis;
15 int control,cost_function,domaintype;
16 int num_controls,num_cost_functions;
20 int *control_enums = NULL;
21 char **controls = NULL;
22 char **cost_functions = NULL;
29 iomodel->
FindConstant(&control_analysis,
"md.inversion.iscontrol");
30 if(!control_analysis)
return;
34 iomodel->
FindConstant(&isautodiff,
"md.autodiff.isautodiff");
41 iomodel->
FindConstant(&num_controls,
"md.inversion.num_control_parameters");
42 iomodel->
FindConstant(&controls,&num_controls,
"md.inversion.control_parameters");
43 if(num_controls<1)
_error_(
"no controls found");
44 control_enums=xNew<int>(num_controls);
45 for(
int i=0;i<num_controls;i++){
50 iomodel->
FindConstant(&num_cost_functions,
"md.inversion.num_cost_functions");
51 iomodel->
FindConstant(&cost_functions,&num_cost_functions,
"md.inversion.cost_functions");
52 if(num_cost_functions<1)
_error_(
"No cost functions found");
53 int* cost_function_enums=xNew<int>(num_cost_functions);
54 for(
int i=0;i<num_cost_functions;++i){
59 iomodel->
FindConstant(&domaintype,
"md.mesh.domain_type");
61 iomodel->
FetchData(&weights,&M,&N,
"md.inversion.cost_functions_coefficients");
65 IssmDouble* weights_transp = xNew<IssmDouble>(M*N);
66 for(
int i=0;i<M;i++)
for(
int j=0;j<N;j++) weights_transp[j*M+i] = weights[i*N+j];
67 xDelete<IssmDouble>(weights);
68 weights = weights_transp;
72 for(
int i=0;i<num_cost_functions;i++){
73 cost_function=cost_function_enums[i];
85 for(
int j=0;j<elements->
Size();j++){
91 xDelete<IssmDouble>(weights);
94 iomodel->
FetchData(&independents_min,&M,&N,
"md.inversion.min_parameters");
96 iomodel->
FetchData(&independents_max,&M,&N,
"md.inversion.max_parameters");
101 IssmDouble* independents_min_transp = xNew<IssmDouble>(M*N);
102 for(
int i=0;i<M;i++)
for(
int j=0;j<N;j++) independents_min_transp[j*M+i] = independents_min[i*N+j];
103 xDelete<IssmDouble>(independents_min);
104 independents_min = independents_min_transp;
106 IssmDouble* independents_max_transp = xNew<IssmDouble>(M*N);
107 for(
int i=0;i<M;i++)
for(
int j=0;j<N;j++) independents_max_transp[j*M+i] = independents_max[i*N+j];
108 xDelete<IssmDouble>(independents_max);
109 independents_max = independents_max_transp;
112 for(
int i=0;i<num_controls;i++){
113 control = control_enums[i];
120 case VxEnum: iomodel->
FetchData(&independent,&M,&N,
"md.initialization.vx");scale = 1./yts;
break;
121 case VyEnum: iomodel->
FetchData(&independent,&M,&N,
"md.initialization.vy");scale = 1./yts;
break;
142 for(
int j=0;j<elements->
Size();j++){
146 xDelete<IssmDouble>(independent);
148 xDelete<IssmDouble>(independents_min);
149 xDelete<IssmDouble>(independents_max);
153 for(
int i=0;i<num_controls;i++){
154 switch(control_enums[i]){
174 xDelete<int>(control_enums);
175 xDelete<int>(cost_function_enums);
176 for(
int i=0;i<num_cost_functions;i++) xDelete<char>(cost_functions[i]);
177 xDelete<char*>(cost_functions);
178 for(
int i=0;i<num_controls;i++) xDelete<char>(controls[i]);
179 xDelete<char*>(controls);
183 #if defined(_HAVE_AD_)
185 int num_independent_objects,M,N,M_par,N_par;
188 int* control_sizes = NULL;
193 bool control_analysis =
false;
195 iomodel->
FindConstant(&control_analysis,
"md.inversion.iscontrol");
198 if(!control_analysis)
return;
201 iomodel->
FetchData(&num_independent_objects,
"md.autodiff.num_independent_objects");
202 _assert_(num_independent_objects>0);
203 iomodel->
FetchData(&names,&M,
"md.autodiff.independent_object_names");
204 _assert_(M==num_independent_objects);
205 iomodel->
FetchData(&types,NULL,NULL,
"md.autodiff.independent_object_types");
207 M_all = xNew<int>(num_independent_objects);
211 iomodel->
FetchData(&independents_fullmin,&M_par,&N_par,
"md.autodiff.independent_min_parameters");
212 iomodel->
FetchData(&independents_fullmax,&M_par,&N_par,
"md.autodiff.independent_max_parameters");
213 iomodel->
FetchData(&control_sizes,NULL,NULL,
"md.autodiff.independent_control_sizes");
215 int* start_point = NULL;
216 start_point = xNew<int>(num_independent_objects);
218 for(
int i=0;i<num_independent_objects;i++){
219 start_point[i]=counter;
220 counter+=control_sizes[i];
223 for(
int i=0;i<num_independent_objects;i++){
228 char* iofieldname = NULL;
236 iomodel->
FetchData(&independent,&M,&N,iofieldname);
240 independents_min = NULL; independents_min = xNew<IssmDouble>(M*N);
241 independents_max = NULL; independents_max = xNew<IssmDouble>(M*N);
242 for(
int m=0;m<M;m++){
243 for(
int n=0;n<N;n++){
244 independents_min[N*m+n]=independents_fullmin[N_par*m+start_point[i]+n];
245 independents_max[N*m+n]=independents_fullmax[N_par*m+start_point[i]+n];
248 if(N!=1) M_all[i]=M-1;
251 for(
int j=0;j<elements->
Size();j++){
253 element->
ControlInputCreate(independent,independents_min,independents_max,inputs2,iomodel,M,N,1.,input_enum,i+1);
255 xDelete<IssmDouble>(independent);
256 xDelete<IssmDouble>(independents_min);
257 xDelete<IssmDouble>(independents_max);
261 _error_(
"Independent cannot be of size " << types[i]);
268 for(
int i=0;i<num_independent_objects;i++){
269 xDelete<char>(names[i]);
271 xDelete<char*>(names);
274 xDelete<IssmDouble>(independents_fullmin);
275 xDelete<IssmDouble>(independents_fullmax);
276 xDelete<int>(start_point);
277 xDelete<int>(control_sizes);