GeoTessCExamples  2.0
PopulateModel3D.c
Go to the documentation of this file.
1 //- ****************************************************************************
2 //-
3 //- Copyright 2009 Sandia Corporation. Under the terms of Contract
4 //- DE-AC04-94AL85000 with Sandia Corporation, the U.S. Government
5 //- retains certain rights in this software.
6 //-
7 //- BSD Open Source License.
8 //- All rights reserved.
9 //-
10 //- Redistribution and use in source and binary forms, with or without
11 //- modification, are permitted provided that the following conditions are met:
12 //-
13 //- * Redistributions of source code must retain the above copyright notice,
14 //- this list of conditions and the following disclaimer.
15 //- * Redistributions in binary form must reproduce the above copyright
16 //- notice, this list of conditions and the following disclaimer in the
17 //- documentation and/or other materials provided with the distribution.
18 //- * Neither the name of Sandia National Laboratories nor the names of its
19 //- contributors may be used to endorse or promote products derived from
20 //- this software without specific prior written permission.
21 //-
22 //- THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
23 //- AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
24 //- IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
25 //- ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
26 //- LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
27 //- CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
28 //- SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
29 //- INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
30 //- CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
31 //- ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
32 //- POSSIBILITY OF SUCH DAMAGE.
33 //-
34 //- ****************************************************************************
35 
36 #include "CpuTimerC.h"
37 #include "GeoTessMetaDataC.h"
38 #include "GeoTessModelC.h"
39 #include "GeoTessUtilsC.h"
40 #include "GeoTessGridC.h"
41 #include "InterpolatorTypeC.h"
42 #include <stdlib.h>
43 #include <stdio.h>
44 #include <string.h>
45 #include "DataTypeC.h"
46 #include "ErrorHandler.h"
47 
48 #define len 1024
49 
50 void errorCheck();
51 
52 /**
53  * A data structure that holds the AK135 velocity model
54  * of Kennett, Engdahl and Buland (1995),
55  * Geophys. J. Int., 122, 108-124.
56  */
57 struct AK135Model
58 {
59  int nLayers;
60  int nRadii[7];
61  float radii[7][50];
62  int nNodes[7];
63  float data[7][50][3];
64 };
65 
66 /**
67  * function that loads the ak135 model into memory from hard
68  * coded information.
69  */
70 void populateAK135(struct AK135Model* ak135);
71 
72 /**
73  * extract the radii from the ak135 model for a single layer.
74  */
75 void getRadii(struct AK135Model* ak135,
76  double* lat, double* lon, int* layer,
77  float* radii, int* nRadii);
78 
79 /**
80  * extract p-velocity, s-velocity and density data from the ak135
81  * model for a single layer.
82  */
83 void getNodeData(struct AK135Model* ak135,
84  double* lat, double* lon, int* layer,
85  float** nodeData, int* nNodes);
86 
87 /**
88  * Populate a 3D model with values from the AK135 Earth model
89  */
90 int main(int argc, char** argv)
91 {
92  char* path;
93  double start, lat, lon;
94  int i, layer, vertexID;
95  GeoTessMetaDataC* metaData;
96  GeoTessModelC* model;
97  GeoTessGridC* grid;
98  int layerTessIds[7];
99  double* vertex;
100  char s[len];
101  char gridFile[len];
102 // char modelFileName[len];
103  char* strTmp;
104 
105  // A source of model data that we can use to populate
106  // our new model. AK135Model is a representation of the 1D
107  // radially symmetric velocity model which we have hardcoded
108  // into this example.
109  struct AK135Model ak135;
110 
111  // radii is a 1D array of floats that can hold a list of
112  // monotonically increasing radius values distributed along
113  // a radial profile that spans a single layer at a single vertex.
114  float* radii;
115  int nRadii;
116 
117  // nodeData is a 2D array of model values with nNodes x nAttributes
118  // elements. nAttributes is always 3, with values for vp, vs and
119  // density. nNodes is the variable number of nodes that describe
120  // the distribution of attribute values along a radial profile
121  // that spans a single layer at a single vertex in the model.
122 
123  float** nodeData;
124  int nNodes;
125  int nAttributes = 3;
126 
127  // allocate memory for radii and nodeData.
128  // The maximum number of radii/nodes it assumed
129  // to be 100.
130  int maxNodes = 100;
131  radii = (float*)malloc(maxNodes*sizeof(float));
132  nodeData = (float**)malloc(maxNodes*sizeof(float*));
133  for (i=0; i<maxNodes; ++i)
134  nodeData[i] = (float*)malloc(nAttributes*sizeof(float));
135 
136  // initialize the ak135 with values that have been hard-coded.
137  // This serves as an example of an Earth model from which values
138  // can be extracted and used to populate our new GeoTessModel.
139  populateAK135(&ak135);
140 
141  printf("%s", "Start populateModel3D ...\n");
142 
143  path = NULL;
144  if(argc != 2){
145  printf("%s\n","Must provide a single command line argument specifying path to the GeoTessModels directory");
146  return -1;
147  }else{
148  path = argv[1];
149  }
150 
151  start = cpu_getCurrCPUTime();
152 
153  metaData = geometadata_create();
154 
155  // specify the ellipsoid to use for converting betweenn geographic and gecentric
156  // coordinates and between radius and depth. This is really not necessary here since
157  // WGS84 is the default, but other options are available.
158  geometadata_setEarthShape(metaData, "WGS84");
159 
160  s[0] = '\0';
161  strncat(s, "Simple example of populating a 3D GeoTess model\n", len);
162  strncat(s, "comprised of 3 multi-level tessellations\n", len);
163  strncat(s, "author: Sandy Ballard\n", len);
164  strncat(s, "contact: sballar@sandia.gov\n", len);
165  strncat(s, "January 2013\n", len);
166  geometadata_setDescription(metaData, s);
167 
168  // Specify a list of layer names.
169  geometadata_setLayerNames1(metaData, (char*)"INNER_CORE; OUTER_CORE; LOWER_MANTLE; TRANSITION_ZONE; UPPER_MANTLE; LOWER_CRUST; UPPER_CRUST");
170 
171  // Specify the relationship between grid tessellations and model layers.
172  // the list has nLayers elements where each element specifies the
173  // index of the multilevel tessellation that supports the
174  // corresponding layer. In this example, the model has
175  // 7 layers and 3 multi-level tessellations.
176  // Layers 0 (inner core) and 1 (outer core) are
177  // supported by tessellation 0 which has 64 degree triangles (huge!)
178  // Layers 2,3 and 4 (3 mantle layer) are supported by tessellation 1
179  // which has 32 degree triangles.
180  // Layers 5 and 6 (crust) are supported by tessellation 2.
181  // which has 16 degree triangles
182  layerTessIds[0] = 0;
183  layerTessIds[1] = 0;
184  layerTessIds[2] = 1;
185  layerTessIds[3] = 1;
186  layerTessIds[4] = 1;
187  layerTessIds[5] = 2;
188  layerTessIds[6] = 2;
189 
190  // set the layerTessIds in the model. setLayerTessIds() must be called after
191  // setLayerNames(), not before.
192  geometadata_setLayerTessIds(metaData, layerTessIds);
193 
194  // specify the names of the attributes and the units of the attributes in
195  // two String arrays.
196  geometadata_setAttributes1(metaData, "Vp; Vs; rho", "km/sec; km/sec; g/cc");
197 
198  // specify the DataType for the data. All attributes, in all profiles, will
199  // have the same data type.
200  geometadata_setDataType1(metaData, FLOAT);
201 
202  errorCheck();
203 
204  // specify the name of the software that is going to generate
205  // the model. This gets stored in the model for future reference.
206  geometadata_setModelSoftwareVersion(metaData, (char*)"GeoTessCExamples.PopulateModel3D 1.0.0");
207 
208  // specify the date when the model was generated. This gets
209  // stored in the model for future reference.
210  strTmp = cpu_now();
211  geometadata_setModelGenerationDate(metaData, strTmp);
212  free(strTmp);
213  strTmp = NULL;
214 
215  // specify the path to the file containing the grid to be use for this test.
216  strncpy(gridFile, path, len);
217  strncat(gridFile, "/small_model_grid.ascii", len);
218 
219  // call a GeoTessModel constructor to build the model. This will build the
220  // grid, and initialize all the data structures to null. To be useful, we
221  // will have to populate the data structures.
222  model = geomodel_create3(gridFile, metaData);
223 
224  errorCheck();
225 
226  // Delete the GeoTessMetaDataC object, which is a wrapper around a C++ GeoTessMetaData
227  // object. Ownership of the underlying C++ GeoTessMetaData object has been transfered
228  // to the newly created GeoTessModel object. The model will delete the C++ GeoTessMetaData
229  // object when it is done with it. We need to delete the memory allocated to the
230  // GeoTessMetaDataC wrapper, but not the wrapped C++ GeoTessMetaData object.
231  // Hence the second parameter is false.
232  geometadata_destroy(metaData);
233 
234  // retrieve a reference to the ellipsoid that is stored in the model. This ellipsoid will be
235  // used to convert betweenn geographic and gecentric coordinates and between radius and depth.
236  EarthShapeC* ellipsoid = geomodel_getEarthShape(model);
237 
238  errorCheck();
239 
240  // retrieve a reference to the grid object.
241  grid = geomodel_getGrid(model);
242 
243  errorCheck();
244 
245  //loop over every vertex of the model.
246  for (vertexID=0; vertexID<geomodel_getNVertices(model); ++vertexID)
247  {
248  // retrieve the unit vector corresponding to the i'th vertex of the grid.
249  vertex = geogrid_getVertex(grid, vertexID);
250 
251  // convert the unit vector to latitude and longitude, in degrees
252  lat = earthshape_getLatDegrees(ellipsoid, vertex);
253  lon = earthshape_getLonDegrees(ellipsoid, vertex);
254 
255  // loop over every layer of the model
256  for (layer=0; layer<geomodel_getNLayers(model); ++layer)
257  {
258  // get the profile radii for the current lat, lon, and layer
259  // from the ak135 earth model.
260  // This is a 1D array of radius values where the first radius is
261  // the radius at the bottom of the layer, the last radius is the
262  // radius of the top of the layer and there can be as many in between
263  // as desired. This function will be different for every real-life
264  // application. In a real application, users would be responsible
265  // for producing radius values appropriate for their model.
266  getRadii(&ak135, &lat, &lon, &layer, radii, &nRadii);
267 
268  // get the profile data values for current lat, lon, layer
269  // from the ak135 earth model.
270  // This is a 2D array of values, nNodes by nAttributes.
271  // In this example, nAttributes is 3 corresponding to
272  // attributes vp, vs and rho. The number of nodes can
273  // vary as a function of vertex and layer, but must
274  // be consistent with the number of radii retrieved with
275  // the getRadii() method called above. In a real
276  // application, users would be responsible for producing
277  // data values appropriate for their model.
278  getNodeData(&ak135, &lat, &lon, &layer, nodeData, &nNodes);
279 
280  // pass the radii and nodeData model values to GeoTessModel.
281  // It will create the right type of Profile object for the
282  // number of radii and nodeData provided:
283  // nRadii == nNodes and both > 1 : ProfileNPoint object.
284  // nRadii == 1 and nNodes == 1 : ProfileThin object.
285  // nRadii == 2 and nNodes == 1 : ProfileConstant object.
286  // nRadii == 2 and nNodes == 0 : ProfileEmpty object.
287  // nRadii == 0 and nNodes == 1 : ProfileSurface object.
288  // Furthermore, if a vertex is not connected to other vertices
289  // by triangles in the given layer, then a ProfileEmpty
290  // object is created, regardless of the values of nRadii and nNodes.
291  // GeoTessProfile objects will copy the radii and nodeData values
292  // from the supplied arrays. The caller (this application)
293  // retains ownership of the arrays and remains responsible for
294  // deallocating their memory.
295  geomodel_setProfileFloats(model, vertexID, layer, radii, nRadii, nodeData, nNodes, nAttributes);
296  }
297  }
298 
299  errorCheck();
300 
301  // we are done with radii and nodeData so delete their memory.
302  free(radii);
303  for (i=0; i<maxNodes; ++i)
304  free(nodeData[i]);
305  free(nodeData);
306 
307  // Now let's write the model out to a file, delete it, reload it from the
308  // same file and test it.
309 
310  // specify the name of the ascii file to which to write the model.
311 
312 // strncpy(modelFileName, path, len);
313 // strncat(modelFileName, "/populate_model_3d.ascii", len);
314 
315  // write the model to a file.
316 
317 // geomodel_writeModel(model, modelFileName);
318 
319  // we are done with this model, free it.
320 // geomodel_destroy(model);
321 
322  // construct a new model by reading the old one back into memory.
323 // model = geomodel_create1(modelFileName, SPEED);
324 
325  // print a bunch of information about the model to the screen.
326  strTmp = geomodel_toString(model);
327  printf("%s\n", strTmp);
328  free(strTmp);
329  strTmp = NULL;
330 
331  earthshape_destroy(ellipsoid);
332 
333  // free the C GeoTessGridC wrapper around the C++ GeoTessGrid object
334  // without freeing the underlying GeoTessGrid. It will be freed by
335  // the GeoTessModel when it gets deleted.
336  geogrid_destroy(grid);
337 
338  // free the C GeoTessModelC wrapper around the C++ GeoTessModel object.
339  // The underlying C++ GeoTessModel object will be deleted as well.
340  geomodel_destroy(model);
341 
342  printf("Cpu Time (msec): %f\n", cpu_getCurrCPUTime() - start);
343  printf("%s", "End of populateModel3D example\n\n");
344 
345  return 0;
346 }
347 
349 {
350  // print out error messages from the message stack,
351  // most recent error first.
352  while (error_exists())
353  {
354  fprintf(stderr, "%s\n", error_getMessage());
355 
356  // if there were any error messages to start with,
357  // and the last error message has been printed,
358  // then exit.
359  if (!error_exists())
360  exit(-1);
361  }
362 }
363 
364 /**
365  * Returns a 1D profile of monotonically increasing radius values
366  * that define the radial positions of nodes along a radial
367  * profile through a single layer in the model. Used by
368  * populateModel3D.
369  * <p>
370  * For this example, we will return the radius positions of the
371  * nodes in the AK135 model, stretched a little bit so that
372  * the top of the model will coincide with the radius of the
373  * WGS84 ellipsoid instead of the ak135 value of 6371 km.
374  * @param ak135 the struct defining the AK135 model.
375  * @param lat the latitude of the profile
376  * @param lon the longitude of the profile
377  * @param layer the index of the layer.
378  * @param radii a 1D array of floats that will be populated
379  * with radius values for the current layer.
380  * @param nRadii the number of radii populated in radii.
381  */
382 void getRadii(struct AK135Model* ak135,
383  double* lat, double* lon, int* layer,
384  float* radii, int* nRadii)
385 {
386  // convert lat, lon in degrees to unit vector.
387  double vertex[3];
388  double earthRadius;
389  float stretch;
390  int i;
391 
392  EarthShapeC* wgs84 = earthshape_create("WGS84");
393 
394  earthshape_getVectorDegrees(wgs84, *lat, *lon, vertex);
395 
396  // find the radius of the WGS84 ellipsoid at the latitude of vertex.
397  earthRadius = earthshape_getEarthRadius(wgs84, vertex);
398 
399  // find a stretching factor that will stretch the radius values so that they
400  // span the range from zero at the center of the earth to the radius of the
401  // WGS84 ellipsoid at the surface of the Earth. This is not geophysically
402  // realistic, but sufficient for this simplistic example.
403  stretch = (float)(earthRadius / 6371.);
404 
405  *nRadii = ak135->nRadii[*layer];
406  for (i=0; i<*nRadii; ++i)
407  radii[i] = ak135->radii[*layer][i] * stretch;
408 
409  earthshape_destroy(wgs84);
410 
411 }
412 
413 /**
414  * Retrieve a 2D array of floats with nNodes x nAttributes elements.
415  * The number of attributes is 3, for the vp, vs and rho. nNodes
416  * varies in the different layers. For core and mantle layers,
417  * nNodes will equal the number of radii in the corresponding
418  * layers of the AK135 model. For the crustal layers, nNodes
419  * will be one, reflecting the fact that the attribute values are
420  * constant in the crustal layers of the ak135 model.
421  * Used by populateModel3D.
422  * <p>
423  * In this example, the data returned are independent of latitude and
424  * longitude since ak135 is a '1D' model, but this will not generally
425  * be true for real 3D models.
426  * @param ak135 the struct defining the AK135 model.
427  * @param lat the latitude of the profile
428  * @param lon the longitude of the profile
429  * @param layer the index of the layer.
430  * @param nodeData an nNodes by nAttributes array of floats that
431  * will be populated with model values from the ak135 model.
432  * @param nNodes the number of nodes in nodeData that got populated.
433  * @return
434  */
435 void getNodeData(struct AK135Model* ak135,
436  double* lat, double* lon, int* layer,
437  float** nodeData, int* nNodes)
438 {
439  int i;
440 
441  *nNodes = ak135->nNodes[*layer];
442  for (i=0; i<*nNodes; ++i)
443  {
444  nodeData[i][0] = ak135->data[*layer][i][0];
445  nodeData[i][1] = ak135->data[*layer][i][1];
446  nodeData[i][2] = ak135->data[*layer][i][2];
447  }
448 }
449 
450 /**
451  * Load hard-coded data for the ak135 velocity model.
452  * Values loaded are radius, p-velocity, s-velocity and density.
453  *
454  */
455 void populateAK135(struct AK135Model* ak135)
456 {
457  ak135->nLayers = 7;
458  ak135->nRadii[0] = 24;
459  ak135->radii[0][ 0] = 0.000F;
460  ak135->radii[0][ 1] = 50.710F;
461  ak135->radii[0][ 2] = 101.430F;
462  ak135->radii[0][ 3] = 152.140F;
463  ak135->radii[0][ 4] = 202.850F;
464  ak135->radii[0][ 5] = 253.560F;
465  ak135->radii[0][ 6] = 304.280F;
466  ak135->radii[0][ 7] = 354.990F;
467  ak135->radii[0][ 8] = 405.700F;
468  ak135->radii[0][ 9] = 456.410F;
469  ak135->radii[0][10] = 507.130F;
470  ak135->radii[0][11] = 557.840F;
471  ak135->radii[0][12] = 659.260F;
472  ak135->radii[0][13] = 709.980F;
473  ak135->radii[0][14] = 760.690F;
474  ak135->radii[0][15] = 811.400F;
475  ak135->radii[0][16] = 862.110F;
476  ak135->radii[0][17] = 912.830F;
477  ak135->radii[0][18] = 963.540F;
478  ak135->radii[0][19] = 1014.250F;
479  ak135->radii[0][20] = 1064.960F;
480  ak135->radii[0][21] = 1115.680F;
481  ak135->radii[0][22] = 1166.390F;
482  ak135->radii[0][23] = 1217.500F;
483  ak135->nRadii[1] = 45;
484  ak135->radii[1][ 0] = 1217.500F;
485  ak135->radii[1][ 1] = 1267.430F;
486  ak135->radii[1][ 2] = 1317.760F;
487  ak135->radii[1][ 3] = 1368.090F;
488  ak135->radii[1][ 4] = 1418.420F;
489  ak135->radii[1][ 5] = 1468.760F;
490  ak135->radii[1][ 6] = 1519.090F;
491  ak135->radii[1][ 7] = 1569.420F;
492  ak135->radii[1][ 8] = 1670.080F;
493  ak135->radii[1][ 9] = 1720.410F;
494  ak135->radii[1][10] = 1770.740F;
495  ak135->radii[1][11] = 1821.070F;
496  ak135->radii[1][12] = 1871.400F;
497  ak135->radii[1][13] = 1921.740F;
498  ak135->radii[1][14] = 1972.070F;
499  ak135->radii[1][15] = 2022.400F;
500  ak135->radii[1][16] = 2072.730F;
501  ak135->radii[1][17] = 2123.060F;
502  ak135->radii[1][18] = 2173.390F;
503  ak135->radii[1][19] = 2223.720F;
504  ak135->radii[1][20] = 2274.050F;
505  ak135->radii[1][21] = 2324.380F;
506  ak135->radii[1][22] = 2374.720F;
507  ak135->radii[1][23] = 2425.050F;
508  ak135->radii[1][24] = 2475.380F;
509  ak135->radii[1][25] = 2525.710F;
510  ak135->radii[1][26] = 2576.040F;
511  ak135->radii[1][27] = 2626.370F;
512  ak135->radii[1][28] = 2676.700F;
513  ak135->radii[1][29] = 2727.030F;
514  ak135->radii[1][30] = 2777.360F;
515  ak135->radii[1][31] = 2827.700F;
516  ak135->radii[1][32] = 2878.030F;
517  ak135->radii[1][33] = 2928.360F;
518  ak135->radii[1][34] = 2978.690F;
519  ak135->radii[1][35] = 3029.020F;
520  ak135->radii[1][36] = 3079.350F;
521  ak135->radii[1][37] = 3129.680F;
522  ak135->radii[1][38] = 3180.010F;
523  ak135->radii[1][39] = 3230.340F;
524  ak135->radii[1][40] = 3280.680F;
525  ak135->radii[1][41] = 3331.010F;
526  ak135->radii[1][42] = 3381.340F;
527  ak135->radii[1][43] = 3431.670F;
528  ak135->radii[1][44] = 3479.500F;
529  ak135->nRadii[2] = 46;
530  ak135->radii[2][ 0] = 3479.500F;
531  ak135->radii[2][ 1] = 3531.670F;
532  ak135->radii[2][ 2] = 3581.330F;
533  ak135->radii[2][ 3] = 3631.000F;
534  ak135->radii[2][ 4] = 3681.000F;
535  ak135->radii[2][ 5] = 3731.000F;
536  ak135->radii[2][ 6] = 3779.500F;
537  ak135->radii[2][ 7] = 3829.000F;
538  ak135->radii[2][ 8] = 3878.500F;
539  ak135->radii[2][ 9] = 3928.000F;
540  ak135->radii[2][10] = 3977.500F;
541  ak135->radii[2][11] = 4027.000F;
542  ak135->radii[2][12] = 4076.500F;
543  ak135->radii[2][13] = 4126.000F;
544  ak135->radii[2][14] = 4175.500F;
545  ak135->radii[2][15] = 4225.000F;
546  ak135->radii[2][16] = 4274.500F;
547  ak135->radii[2][17] = 4324.000F;
548  ak135->radii[2][18] = 4373.500F;
549  ak135->radii[2][19] = 4423.000F;
550  ak135->radii[2][20] = 4472.500F;
551  ak135->radii[2][21] = 4522.000F;
552  ak135->radii[2][22] = 4571.500F;
553  ak135->radii[2][23] = 4621.000F;
554  ak135->radii[2][24] = 4670.500F;
555  ak135->radii[2][25] = 4720.000F;
556  ak135->radii[2][26] = 4769.500F;
557  ak135->radii[2][27] = 4819.000F;
558  ak135->radii[2][28] = 4868.500F;
559  ak135->radii[2][29] = 4918.000F;
560  ak135->radii[2][30] = 4967.500F;
561  ak135->radii[2][31] = 5017.000F;
562  ak135->radii[2][32] = 5066.500F;
563  ak135->radii[2][33] = 5116.000F;
564  ak135->radii[2][34] = 5165.500F;
565  ak135->radii[2][35] = 5215.000F;
566  ak135->radii[2][36] = 5264.500F;
567  ak135->radii[2][37] = 5314.000F;
568  ak135->radii[2][38] = 5363.500F;
569  ak135->radii[2][39] = 5413.000F;
570  ak135->radii[2][40] = 5462.500F;
571  ak135->radii[2][41] = 5512.000F;
572  ak135->radii[2][42] = 5561.500F;
573  ak135->radii[2][43] = 5611.000F;
574  ak135->radii[2][44] = 5661.000F;
575  ak135->radii[2][45] = 5711.000F;
576  ak135->nRadii[3] = 6;
577  ak135->radii[3][ 0] = 5711.000F;
578  ak135->radii[3][ 1] = 5761.000F;
579  ak135->radii[3][ 2] = 5811.000F;
580  ak135->radii[3][ 3] = 5861.000F;
581  ak135->radii[3][ 4] = 5911.000F;
582  ak135->radii[3][ 5] = 5961.000F;
583  ak135->nRadii[4] = 9;
584  ak135->radii[4][ 0] = 5961.000F;
585  ak135->radii[4][ 1] = 6011.000F;
586  ak135->radii[4][ 2] = 6061.000F;
587  ak135->radii[4][ 3] = 6111.000F;
588  ak135->radii[4][ 4] = 6161.000F;
589  ak135->radii[4][ 5] = 6206.000F;
590  ak135->radii[4][ 6] = 6251.000F;
591  ak135->radii[4][ 7] = 6293.500F;
592  ak135->radii[4][ 8] = 6336.000F;
593  ak135->nRadii[5] = 2;
594  ak135->radii[5][ 0] = 6336.000F;
595  ak135->radii[5][ 1] = 6351.000F;
596  ak135->nRadii[6] = 2;
597  ak135->radii[6][ 0] = 6351.000F;
598  ak135->radii[6][ 1] = 6371.000F;
599 
600  ak135->nNodes[0] = 24;
601  ak135->data[0][ 0][0] = 11.2622F; ak135->data[0][ 0][1] = 3.6678F; ak135->data[0][ 0][2] = 13.0122F;
602  ak135->data[0][ 1][0] = 11.2618F; ak135->data[0][ 1][1] = 3.6675F; ak135->data[0][ 1][2] = 13.0117F;
603  ak135->data[0][ 2][0] = 11.2606F; ak135->data[0][ 2][1] = 3.6667F; ak135->data[0][ 2][2] = 13.0100F;
604  ak135->data[0][ 3][0] = 11.2586F; ak135->data[0][ 3][1] = 3.6653F; ak135->data[0][ 3][2] = 13.0074F;
605  ak135->data[0][ 4][0] = 11.2557F; ak135->data[0][ 4][1] = 3.6633F; ak135->data[0][ 4][2] = 13.0036F;
606  ak135->data[0][ 5][0] = 11.2521F; ak135->data[0][ 5][1] = 3.6608F; ak135->data[0][ 5][2] = 12.9988F;
607  ak135->data[0][ 6][0] = 11.2477F; ak135->data[0][ 6][1] = 3.6577F; ak135->data[0][ 6][2] = 12.9929F;
608  ak135->data[0][ 7][0] = 11.2424F; ak135->data[0][ 7][1] = 3.6540F; ak135->data[0][ 7][2] = 12.9859F;
609  ak135->data[0][ 8][0] = 11.2364F; ak135->data[0][ 8][1] = 3.6498F; ak135->data[0][ 8][2] = 12.9779F;
610  ak135->data[0][ 9][0] = 11.2295F; ak135->data[0][ 9][1] = 3.6450F; ak135->data[0][ 9][2] = 12.9688F;
611  ak135->data[0][10][0] = 11.2219F; ak135->data[0][10][1] = 3.6396F; ak135->data[0][10][2] = 12.9586F;
612  ak135->data[0][11][0] = 11.2134F; ak135->data[0][11][1] = 3.6337F; ak135->data[0][11][2] = 12.9474F;
613  ak135->data[0][12][0] = 11.1941F; ak135->data[0][12][1] = 3.6202F; ak135->data[0][12][2] = 12.9217F;
614  ak135->data[0][13][0] = 11.1832F; ak135->data[0][13][1] = 3.6126F; ak135->data[0][13][2] = 12.9072F;
615  ak135->data[0][14][0] = 11.1715F; ak135->data[0][14][1] = 3.6044F; ak135->data[0][14][2] = 12.8917F;
616  ak135->data[0][15][0] = 11.1590F; ak135->data[0][15][1] = 3.5957F; ak135->data[0][15][2] = 12.8751F;
617  ak135->data[0][16][0] = 11.1457F; ak135->data[0][16][1] = 3.5864F; ak135->data[0][16][2] = 12.8574F;
618  ak135->data[0][17][0] = 11.1316F; ak135->data[0][17][1] = 3.5765F; ak135->data[0][17][2] = 12.8387F;
619  ak135->data[0][18][0] = 11.1166F; ak135->data[0][18][1] = 3.5661F; ak135->data[0][18][2] = 12.8188F;
620  ak135->data[0][19][0] = 11.0983F; ak135->data[0][19][1] = 3.5551F; ak135->data[0][19][2] = 12.7980F;
621  ak135->data[0][20][0] = 11.0850F; ak135->data[0][20][1] = 3.5435F; ak135->data[0][20][2] = 12.7760F;
622  ak135->data[0][21][0] = 11.0718F; ak135->data[0][21][1] = 3.5314F; ak135->data[0][21][2] = 12.7530F;
623  ak135->data[0][22][0] = 11.0585F; ak135->data[0][22][1] = 3.5187F; ak135->data[0][22][2] = 12.7289F;
624  ak135->data[0][23][0] = 11.0427F; ak135->data[0][23][1] = 3.5043F; ak135->data[0][23][2] = 12.7037F;
625  ak135->nNodes[1] = 45;
626  ak135->data[1][ 0][0] = 10.2890F; ak135->data[1][ 0][1] = 0.0000F; ak135->data[1][ 0][2] = 12.1391F;
627  ak135->data[1][ 1][0] = 10.2854F; ak135->data[1][ 1][1] = 0.0000F; ak135->data[1][ 1][2] = 12.1133F;
628  ak135->data[1][ 2][0] = 10.2745F; ak135->data[1][ 2][1] = 0.0000F; ak135->data[1][ 2][2] = 12.0867F;
629  ak135->data[1][ 3][0] = 10.2565F; ak135->data[1][ 3][1] = 0.0000F; ak135->data[1][ 3][2] = 12.0593F;
630  ak135->data[1][ 4][0] = 10.2329F; ak135->data[1][ 4][1] = 0.0000F; ak135->data[1][ 4][2] = 12.0311F;
631  ak135->data[1][ 5][0] = 10.2049F; ak135->data[1][ 5][1] = 0.0000F; ak135->data[1][ 5][2] = 12.0001F;
632  ak135->data[1][ 6][0] = 10.1739F; ak135->data[1][ 6][1] = 0.0000F; ak135->data[1][ 6][2] = 11.9722F;
633  ak135->data[1][ 7][0] = 10.1415F; ak135->data[1][ 7][1] = 0.0000F; ak135->data[1][ 7][2] = 11.9414F;
634  ak135->data[1][ 8][0] = 10.0768F; ak135->data[1][ 8][1] = 0.0000F; ak135->data[1][ 8][2] = 11.8772F;
635  ak135->data[1][ 9][0] = 10.0439F; ak135->data[1][ 9][1] = 0.0000F; ak135->data[1][ 9][2] = 11.8437F;
636  ak135->data[1][10][0] = 10.0103F; ak135->data[1][10][1] = 0.0000F; ak135->data[1][10][2] = 11.8092F;
637  ak135->data[1][11][0] = 9.9761F; ak135->data[1][11][1] = 0.0000F; ak135->data[1][11][2] = 11.7737F;
638  ak135->data[1][12][0] = 9.9410F; ak135->data[1][12][1] = 0.0000F; ak135->data[1][12][2] = 11.7373F;
639  ak135->data[1][13][0] = 9.9051F; ak135->data[1][13][1] = 0.0000F; ak135->data[1][13][2] = 11.6998F;
640  ak135->data[1][14][0] = 9.8682F; ak135->data[1][14][1] = 0.0000F; ak135->data[1][14][2] = 11.6612F;
641  ak135->data[1][15][0] = 9.8304F; ak135->data[1][15][1] = 0.0000F; ak135->data[1][15][2] = 11.6216F;
642  ak135->data[1][16][0] = 9.7914F; ak135->data[1][16][1] = 0.0000F; ak135->data[1][16][2] = 11.5809F;
643  ak135->data[1][17][0] = 9.7513F; ak135->data[1][17][1] = 0.0000F; ak135->data[1][17][2] = 11.5391F;
644  ak135->data[1][18][0] = 9.7100F; ak135->data[1][18][1] = 0.0000F; ak135->data[1][18][2] = 11.4962F;
645  ak135->data[1][19][0] = 9.6673F; ak135->data[1][19][1] = 0.0000F; ak135->data[1][19][2] = 11.4521F;
646  ak135->data[1][20][0] = 9.6232F; ak135->data[1][20][1] = 0.0000F; ak135->data[1][20][2] = 11.4069F;
647  ak135->data[1][21][0] = 9.5777F; ak135->data[1][21][1] = 0.0000F; ak135->data[1][21][2] = 11.3604F;
648  ak135->data[1][22][0] = 9.5306F; ak135->data[1][22][1] = 0.0000F; ak135->data[1][22][2] = 11.3127F;
649  ak135->data[1][23][0] = 9.4814F; ak135->data[1][23][1] = 0.0000F; ak135->data[1][23][2] = 11.2639F;
650  ak135->data[1][24][0] = 9.4297F; ak135->data[1][24][1] = 0.0000F; ak135->data[1][24][2] = 11.2137F;
651  ak135->data[1][25][0] = 9.3760F; ak135->data[1][25][1] = 0.0000F; ak135->data[1][25][2] = 11.1623F;
652  ak135->data[1][26][0] = 9.3205F; ak135->data[1][26][1] = 0.0000F; ak135->data[1][26][2] = 11.1095F;
653  ak135->data[1][27][0] = 9.2634F; ak135->data[1][27][1] = 0.0000F; ak135->data[1][27][2] = 11.0555F;
654  ak135->data[1][28][0] = 9.2042F; ak135->data[1][28][1] = 0.0000F; ak135->data[1][28][2] = 11.0001F;
655  ak135->data[1][29][0] = 9.1426F; ak135->data[1][29][1] = 0.0000F; ak135->data[1][29][2] = 10.9434F;
656  ak135->data[1][30][0] = 9.0792F; ak135->data[1][30][1] = 0.0000F; ak135->data[1][30][2] = 10.8852F;
657  ak135->data[1][31][0] = 9.0138F; ak135->data[1][31][1] = 0.0000F; ak135->data[1][31][2] = 10.8257F;
658  ak135->data[1][32][0] = 8.9461F; ak135->data[1][32][1] = 0.0000F; ak135->data[1][32][2] = 10.7647F;
659  ak135->data[1][33][0] = 8.8761F; ak135->data[1][33][1] = 0.0000F; ak135->data[1][33][2] = 10.7023F;
660  ak135->data[1][34][0] = 8.8036F; ak135->data[1][34][1] = 0.0000F; ak135->data[1][34][2] = 10.6385F;
661  ak135->data[1][35][0] = 8.7283F; ak135->data[1][35][1] = 0.0000F; ak135->data[1][35][2] = 10.5731F;
662  ak135->data[1][36][0] = 8.6496F; ak135->data[1][36][1] = 0.0000F; ak135->data[1][36][2] = 10.5062F;
663  ak135->data[1][37][0] = 8.5692F; ak135->data[1][37][1] = 0.0000F; ak135->data[1][37][2] = 10.4378F;
664  ak135->data[1][38][0] = 8.4861F; ak135->data[1][38][1] = 0.0000F; ak135->data[1][38][2] = 10.3679F;
665  ak135->data[1][39][0] = 8.4001F; ak135->data[1][39][1] = 0.0000F; ak135->data[1][39][2] = 10.2964F;
666  ak135->data[1][40][0] = 8.3122F; ak135->data[1][40][1] = 0.0000F; ak135->data[1][40][2] = 10.2233F;
667  ak135->data[1][41][0] = 8.2213F; ak135->data[1][41][1] = 0.0000F; ak135->data[1][41][2] = 10.1485F;
668  ak135->data[1][42][0] = 8.1283F; ak135->data[1][42][1] = 0.0000F; ak135->data[1][42][2] = 10.0722F;
669  ak135->data[1][43][0] = 8.0382F; ak135->data[1][43][1] = 0.0000F; ak135->data[1][43][2] = 9.9942F;
670  ak135->data[1][44][0] = 8.0000F; ak135->data[1][44][1] = 0.0000F; ak135->data[1][44][2] = 9.9145F;
671  ak135->nNodes[2] = 46;
672  ak135->data[2][ 0][0] = 13.6602F; ak135->data[2][ 0][1] = 7.2811F; ak135->data[2][ 0][2] = 5.5515F;
673  ak135->data[2][ 1][0] = 13.6566F; ak135->data[2][ 1][1] = 7.2704F; ak135->data[2][ 1][2] = 5.5284F;
674  ak135->data[2][ 2][0] = 13.6530F; ak135->data[2][ 2][1] = 7.2597F; ak135->data[2][ 2][2] = 5.5051F;
675  ak135->data[2][ 3][0] = 13.6494F; ak135->data[2][ 3][1] = 7.2490F; ak135->data[2][ 3][2] = 5.4817F;
676  ak135->data[2][ 4][0] = 13.5900F; ak135->data[2][ 4][1] = 7.2258F; ak135->data[2][ 4][2] = 5.4582F;
677  ak135->data[2][ 5][0] = 13.5312F; ak135->data[2][ 5][1] = 7.2031F; ak135->data[2][ 5][2] = 5.4345F;
678  ak135->data[2][ 6][0] = 13.4741F; ak135->data[2][ 6][1] = 7.1807F; ak135->data[2][ 6][2] = 5.4108F;
679  ak135->data[2][ 7][0] = 13.4156F; ak135->data[2][ 7][1] = 7.1586F; ak135->data[2][ 7][2] = 5.3869F;
680  ak135->data[2][ 8][0] = 13.3585F; ak135->data[2][ 8][1] = 7.1369F; ak135->data[2][ 8][2] = 5.3628F;
681  ak135->data[2][ 9][0] = 13.3018F; ak135->data[2][ 9][1] = 7.1144F; ak135->data[2][ 9][2] = 5.3386F;
682  ak135->data[2][10][0] = 13.2465F; ak135->data[2][10][1] = 7.0931F; ak135->data[2][10][2] = 5.3142F;
683  ak135->data[2][11][0] = 13.1894F; ak135->data[2][11][1] = 7.0720F; ak135->data[2][11][2] = 5.2898F;
684  ak135->data[2][12][0] = 13.1336F; ak135->data[2][12][1] = 7.0500F; ak135->data[2][12][2] = 5.2651F;
685  ak135->data[2][13][0] = 13.0783F; ak135->data[2][13][1] = 7.0281F; ak135->data[2][13][2] = 5.2403F;
686  ak135->data[2][14][0] = 13.0222F; ak135->data[2][14][1] = 7.0063F; ak135->data[2][14][2] = 5.2154F;
687  ak135->data[2][15][0] = 12.9668F; ak135->data[2][15][1] = 6.9855F; ak135->data[2][15][2] = 5.1904F;
688  ak135->data[2][16][0] = 12.9096F; ak135->data[2][16][1] = 6.9627F; ak135->data[2][16][2] = 5.1652F;
689  ak135->data[2][17][0] = 12.8526F; ak135->data[2][17][1] = 6.9418F; ak135->data[2][17][2] = 5.1398F;
690  ak135->data[2][18][0] = 12.7956F; ak135->data[2][18][1] = 6.9194F; ak135->data[2][18][2] = 5.1143F;
691  ak135->data[2][19][0] = 12.7382F; ak135->data[2][19][1] = 6.8972F; ak135->data[2][19][2] = 5.0887F;
692  ak135->data[2][20][0] = 12.6804F; ak135->data[2][20][1] = 6.8742F; ak135->data[2][20][2] = 5.0629F;
693  ak135->data[2][21][0] = 12.6221F; ak135->data[2][21][1] = 6.8515F; ak135->data[2][21][2] = 5.0370F;
694  ak135->data[2][22][0] = 12.5631F; ak135->data[2][22][1] = 6.8286F; ak135->data[2][22][2] = 5.0109F;
695  ak135->data[2][23][0] = 12.5031F; ak135->data[2][23][1] = 6.8052F; ak135->data[2][23][2] = 4.9847F;
696  ak135->data[2][24][0] = 12.4426F; ak135->data[2][24][1] = 6.7815F; ak135->data[2][24][2] = 4.9584F;
697  ak135->data[2][25][0] = 12.3819F; ak135->data[2][25][1] = 6.7573F; ak135->data[2][25][2] = 4.9319F;
698  ak135->data[2][26][0] = 12.3185F; ak135->data[2][26][1] = 6.7326F; ak135->data[2][26][2] = 4.9052F;
699  ak135->data[2][27][0] = 12.2550F; ak135->data[2][27][1] = 6.7073F; ak135->data[2][27][2] = 4.8785F;
700  ak135->data[2][28][0] = 12.1912F; ak135->data[2][28][1] = 6.6815F; ak135->data[2][28][2] = 4.8515F;
701  ak135->data[2][29][0] = 12.1245F; ak135->data[2][29][1] = 6.6555F; ak135->data[2][29][2] = 4.8245F;
702  ak135->data[2][30][0] = 12.0577F; ak135->data[2][30][1] = 6.6285F; ak135->data[2][30][2] = 4.7973F;
703  ak135->data[2][31][0] = 11.9895F; ak135->data[2][31][1] = 6.6008F; ak135->data[2][31][2] = 4.7699F;
704  ak135->data[2][32][0] = 11.9200F; ak135->data[2][32][1] = 6.5727F; ak135->data[2][32][2] = 4.7424F;
705  ak135->data[2][33][0] = 11.8491F; ak135->data[2][33][1] = 6.5439F; ak135->data[2][33][2] = 4.7148F;
706  ak135->data[2][34][0] = 11.7766F; ak135->data[2][34][1] = 6.5138F; ak135->data[2][34][2] = 4.6870F;
707  ak135->data[2][35][0] = 11.7026F; ak135->data[2][35][1] = 6.4828F; ak135->data[2][35][2] = 4.6591F;
708  ak135->data[2][36][0] = 11.6269F; ak135->data[2][36][1] = 6.4510F; ak135->data[2][36][2] = 4.6310F;
709  ak135->data[2][37][0] = 11.5495F; ak135->data[2][37][1] = 6.4187F; ak135->data[2][37][2] = 4.6028F;
710  ak135->data[2][38][0] = 11.4705F; ak135->data[2][38][1] = 6.3854F; ak135->data[2][38][2] = 4.5744F;
711  ak135->data[2][39][0] = 11.3896F; ak135->data[2][39][1] = 6.3512F; ak135->data[2][39][2] = 4.5459F;
712  ak135->data[2][40][0] = 11.3068F; ak135->data[2][40][1] = 6.3160F; ak135->data[2][40][2] = 4.5173F;
713  ak135->data[2][41][0] = 11.2221F; ak135->data[2][41][1] = 6.2798F; ak135->data[2][41][2] = 4.4885F;
714  ak135->data[2][42][0] = 11.1353F; ak135->data[2][42][1] = 6.2426F; ak135->data[2][42][2] = 4.4596F;
715  ak135->data[2][43][0] = 11.0558F; ak135->data[2][43][1] = 6.2095F; ak135->data[2][43][2] = 4.4305F;
716  ak135->data[2][44][0] = 10.9229F; ak135->data[2][44][1] = 6.0897F; ak135->data[2][44][2] = 4.4010F;
717  ak135->data[2][45][0] = 10.7900F; ak135->data[2][45][1] = 5.9600F; ak135->data[2][45][2] = 4.3714F;
718  ak135->nNodes[3] = 6;
719  ak135->data[3][ 0][0] = 10.2000F; ak135->data[3][ 0][1] = 5.6100F; ak135->data[3][ 0][2] = 4.0646F;
720  ak135->data[3][ 1][0] = 10.0320F; ak135->data[3][ 1][1] = 5.5040F; ak135->data[3][ 1][2] = 4.0028F;
721  ak135->data[3][ 2][0] = 9.8640F; ak135->data[3][ 2][1] = 5.3980F; ak135->data[3][ 2][2] = 3.9410F;
722  ak135->data[3][ 3][0] = 9.6960F; ak135->data[3][ 3][1] = 5.2920F; ak135->data[3][ 3][2] = 3.8793F;
723  ak135->data[3][ 4][0] = 9.5280F; ak135->data[3][ 4][1] = 5.1860F; ak135->data[3][ 4][2] = 3.8175F;
724  ak135->data[3][ 5][0] = 9.3600F; ak135->data[3][ 5][1] = 5.0800F; ak135->data[3][ 5][2] = 3.7557F;
725  ak135->nNodes[4] = 9;
726  ak135->data[4][ 0][0] = 9.0300F; ak135->data[4][ 0][1] = 4.8700F; ak135->data[4][ 0][2] = 3.5470F;
727  ak135->data[4][ 1][0] = 8.8475F; ak135->data[4][ 1][1] = 4.7830F; ak135->data[4][ 1][2] = 3.5167F;
728  ak135->data[4][ 2][0] = 8.6650F; ak135->data[4][ 2][1] = 4.6960F; ak135->data[4][ 2][2] = 3.4864F;
729  ak135->data[4][ 3][0] = 8.4825F; ak135->data[4][ 3][1] = 4.6090F; ak135->data[4][ 3][2] = 3.4561F;
730  ak135->data[4][ 4][0] = 8.3000F; ak135->data[4][ 4][1] = 4.5230F; ak135->data[4][ 4][2] = 3.4258F;
731  ak135->data[4][ 5][0] = 8.1750F; ak135->data[4][ 5][1] = 4.5090F; ak135->data[4][ 5][2] = 3.3985F;
732  ak135->data[4][ 6][0] = 8.0500F; ak135->data[4][ 6][1] = 4.5000F; ak135->data[4][ 6][2] = 3.3713F;
733  ak135->data[4][ 7][0] = 8.0450F; ak135->data[4][ 7][1] = 4.4900F; ak135->data[4][ 7][2] = 3.3455F;
734  ak135->data[4][ 8][0] = 8.0400F; ak135->data[4][ 8][1] = 4.4800F; ak135->data[4][ 8][2] = 3.3198F;
735  ak135->nNodes[5] = 1;
736  ak135->data[5][ 0][0] = 6.5000F; ak135->data[5][ 0][1] = 3.8500F; ak135->data[5][ 0][2] = 2.9200F;
737  ak135->nNodes[6] = 1;
738  ak135->data[6][ 0][0] = 5.8000F; ak135->data[6][ 0][1] = 3.4600F; ak135->data[6][ 0][2] = 2.7200F;
739 }
AK135Model::data
float data[7][50][3]
Definition: PopulateModel3D.c:63
AK135Model
Definition: PopulateModel3D.c:58
main
int main(int argc, char **argv)
Definition: PopulateModel3D.c:90
errorCheck
void errorCheck()
Definition: PopulateModel3D.c:348
getNodeData
void getNodeData(struct AK135Model *ak135, double *lat, double *lon, int *layer, float **nodeData, int *nNodes)
Definition: PopulateModel3D.c:435
populateAK135
void populateAK135(struct AK135Model *ak135)
Definition: PopulateModel3D.c:455
AK135Model::nLayers
int nLayers
Definition: PopulateModel3D.c:59
AK135Model::nRadii
int nRadii[7]
Definition: PopulateModel3D.c:60
len
#define len
Definition: PopulateModel3D.c:48
getRadii
void getRadii(struct AK135Model *ak135, double *lat, double *lon, int *layer, float *radii, int *nRadii)
Definition: PopulateModel3D.c:382
AK135Model::radii
float radii[7][50]
Definition: PopulateModel3D.c:61
AK135Model::nNodes
int nNodes[7]
Definition: PopulateModel3D.c:62