NASA Logo
Ocean Color Science Software

ocssw V2022
metqc.c
Go to the documentation of this file.
1 /*****************************************************************
2  * FILE: metqc.c
3  *
4  * PURPOSE: QC HDF ancillary real time datafile against climatology
5  * for one of four parameters.
6  *
7  * DESCRIPTION: This program will create a HDF with:
8  *
9  * HDF Geometry Vdata of Lat/Lon limits and steps.
10  * 2-D std dev of NRT vs CLM for z_wind or,
11  * 2-D std dev of NRT vs CLM for m_wind or,
12  * 2-D std dev of NRT vs CLM for press or,
13  * 2-D std dev of NRT vs CLM for rel_hum.
14  *
15  * A ASCII text file of %points in each STD category.
16  *
17  * For MET data:
18  * The real time parameter is read into array
19  * z_windRT, m_windRT, pressRT or rel_humRT
20  *
21  * Real-time files are dimensioned 73x144. The COADS based
22  * climatology is 90x180. A regridded COADS climatology
23  * (S19461990_COADS.REGRID.MET) is therefore used by this program.
24  *
25  * The climatological averages and standard deviations for the same time
26  * period (month) are read into:
27  * z_windCLMAVG, m_windCLMAVG, pressCLMAVG or rel_humCLMAVG and
28  * z_windCLMSTD, m_windCLMAVG, pressCLMSTD or rel_humCLMSTD respectively.
29 
30  *
31  * PROCEDURE:
32  *
33  * The CLMAVG array is subtracted from the RT array and
34  * divided by the CLMSTD array to produce an array of the number
35  * of std deviations from the mean for the real-time data.
36  *
37  * An option for an array of just the differences can be run by envoking
38  * the 'd' (difference) flag on the command line.
39  *
40  * As the data is processed a tally of points falling + and - 1, 2, and 3
41  * STDs from the mean will be stored for later writing of percentages in
42  * each category (if 'difference' option not used).
43  *
44  * INPUT PARMS: command line arguments (argv[?])
45  * [1] char *nrtfile - real-time input file to process
46  * ("S199310200_NMC.MET")
47  * [2] char *climfile - regridded climatology input file to process
48  * ("S19461990_COADS.REGRID.MET")
49  * [3] char *outfile - output QC filename.
50  * Note: FNOC could be used in place of NMC.
51  * [4] char monthstr - month being processed
52  * [5] - field to compare: 'z_wind', 'm_wind', 'press', 'rel_hum' or 'p_water'
53  * [6] float32 stdlimit1 - % w/in 1 STD
54  * [7] float32 stdlimit2 - % w/in 2 STD
55  * [8] float32 stdlimit3 - % w/in 3 STD
56  * [9] int maxmissing - max num missing pts.
57  *
58  * Optional inputs: on command line
59  * (args are read in order so preceeding optionals are required in order
60  * to use succeeding ones.)
61  *
62  * [10] float32 loval - lowest allowed value
63  * [11] float32 hival - highest allowed value
64  * [12] int outmax - max num allowed outliers before error flag set.
65  * [13] char gridflag - 'S'tandard deviation [default] or 'D'ifference calc.
66  * Note, difference calculations do not product reports.
67  * [14] int ifileflag - 0 = file is NRT file [default],
68  * 1 = file in CLM file (stats on one CLM vs another)
69  *
70  * OUTPUT PARMS:
71  * prints report to standard out.
72  * returns a SUCCESS (0) or FAILURE(5) value as Standard Deviation
73  * threshold exit status. This value can be checked with a C-shell
74  * $status flag.
75  *
76  * output name is similar to the input real-time file.
77  * Example name: "S199310200_NMC.MET.'parm'.qc"
78  * ('parm' = z_wind, m_wind, press, rel_hum or p_water)
79  *
80  * RETURNS: Program returns success or failure codes to a calling
81  * 'shell' script.
82  *
83  * LOCAL VARS: variables for storing HDFs.
84  *
85  * Subs called: int rdsds - reads an HDF SDS data grid
86  * int8 check_usage - confirm args
87  * int startHDF - open HDF file for output
88  * int setupGrid - setup HDF geometry struct
89  * int writeGeom - write HDF geometry struct
90  * int wrtsds - write HDF SDS array
91  * int addAttr - add HDF SDS attributes
92  * int setSDSref - set HDF SDS reference
93  * void deattachHDFgrid - detach HDF grid struct
94  * int closeHDFstructs - close HDF files
95  * int rd_size - read field size
96  * int resize_2d - resize climatology field to match nrt
97  *
98  * HISTORY: none
99  *
100  * NOTE: This program is meant to generate HDF QC SDS data sets.
101  *
102  * AUTHOR: Brian D. Schieber, GSC, 4/93
103  *
104  * MODIFICATION HISTORY:
105  *
106  * 10/14/93 BDS - Subtantial mods to process all three MET parameters
107  * at once and to handle the NEW HDF format specs.
108  * 12/06/93 BDS - Make that all 4 parms (z_wind,m_wind,press,rel_hum).
109  * Verifying the exclusion of missings from CLM in
110  * these calcs (in NRT, 0.0's passed through).
111  * Defined VALIDMIN to -99.1 (catches CDFMINVAL (-99.9)
112  * in CLM) as min threshold for QC valid points to
113  * calculate.
114  * 3/94 BDS - prep for call from script which used SYBASE calls.
115  * Append parm type to 'qc' file name.
116  * Return pass or fail STD DEV thresholds as file status.
117  * 5/94 BDS - allow specification of output directory
118  * 8/14/95 BDS - revised for OAPS spec 2.7
119  * 11/95 BDS, add ability to sum number of values in image < or >
120  * two specified range arguments and return FAIL if > outmax.
121  * Values for LO(lower range), HI (upper range),
122  * and OUTMAX (MAX. Pts allowed outside range) hardcoded within
123  * for each of the four parameters.
124  * Also, print min and max value of data.
125  * 8/21/96 BDS - renamed 'perror' to 'pexit' to avoid HDF4.0 conflict.
126  * W. Robinson, GSC, 6 Feb 97 add p_water and make code work independently
127  * of the nrt and climatology sizes
128  *****************************************************************/
129 #include <mfhdf.h>
130 
131 #include "ancil.h"
132 #include "l1io.h"
133 #include <genutils.h>
134 
135 /*
136  * Note on all data sizes: old (pre march 97) data sizes
137  * met nrt: 73 lines, 144 pixels
138  * met climatology: 90 lines, 180 pixels
139  * met climatology gridded: 73 lines, 144 pixels - same as nrt
140  */
141 /*
142  * MET specific settings
143  */
144 
145 #define VGROUPCLASS "PlanetaryGrid" /* all inner Vgroups use same name */
146 
147 #define BIN_METH 2 /* geometry structure settings */
148 #define REGISTRATION CENTER /* " */
149 
150 /* MET file settings */
151 #define VSIZE 2.5 /* " */
152 #define HSIZE 2.5 /* " */
153 #define MAX_NORTH 89.0 /* " */
154 #define MAX_SOUTH -89.0 /* " */
155 #define MAX_WEST -179.0 /* " */
156 #define MAX_EAST 179.0 /* " */
157 
158 #define VALIDMIN -99.1 /* using '.1' to compensate float */
159 #define CLMfile 1
160 
162 
163 int main(int argc, char *argv[]) {
164  int i, j, p;
165  int rank;
166  int result = 0;
167  int missing = 0;
168 
169  float32 minval = 1200.0; /* initial minimum value */
170  float32 maxval = -100.0; /* initial maximum value */
171 
172  float32 loZ_WIND = -30.0; /* default lo range threshold */
173  float32 hiZ_WIND = 30.0; /* default hi range threshold */
174  float32 loM_WIND = -30.0; /* default lo range threshold */
175  float32 hiM_WIND = 30.0; /* default hi range threshold */
176  float32 loPRESS = 850.0; /* default lo range threshold */
177  float32 hiPRESS = 1100.0; /* default hi range threshold */
178  float32 loREL_HUM = 5.0; /* default lo range threshold */
179  float32 hiREL_HUM = 100.0; /* default hi range threshold */
180  float32 loP_WATER = 0.; /* as above precip. water */
181  float32 hiP_WATER = 200.;
182  float32 loval; /* default actual range threshold */
183  float32 hival; /* default actual range threshold */
184  int outmax = 25; /* max num pts allowed to fall
185  outside range */
186 
187  int locnt; /* pts under lo range limit */
188  int hicnt; /* pts above hi range limit */
189  int rtmiss = 0;
190  int totalpts = 0;
191  int neg1cnt = 0;
192  int neg2cnt = 0;
193  int neg3cnt = 0;
194  int pos1cnt = 0;
195  int pos2cnt = 0;
196  int pos3cnt = 0;
197  int failed = 0;
198  int array_size = 0;
199  int32 shape_nrt[2], shape_clm[2];
200  int32 inShape[2];
201  char infileRT[MAXNAMELNG];
202  char infileCLM[MAXNAMELNG];
203  char outfile[MAXNAMELNG];
204  char gridflag[2];
205  char datalabel[MAXNAMELNG];
206  int32 datatype;
207  char *dataattr;
208  char *dataunit;
209  char vgname[MAXNAMELNG];
210  char monthstr[13];
211  char sdsname[MAXNAMELNG];
212  char vgroupname[21];
213  int32 sdsid, sdfid, fid, gridid, geomid;
214  int ifileflag = 0;
215  float32 stdlimit1, stdlimit2, stdlimit3;
216  int maxmissing;
217  /*
218  * data type array pointers
219  */
220 
221  float32 *float_SDSdataRT;
222  float32 *float_SDSdataCLMAVG;
223  float32 *float_SDSdataCLMSTD;
224  float32 *float_SDSdataQC;
225  float32 *c_avg, *c_std; /* new avg, std dev for pre-resized climatology */
226 
227  /* functions used from this file */
228 
229  int8 check_usage();
230 
231  int resize_2d(float *, int, int, int, int, float *);
232  int rd_size(char *, int *, int *);
233 
234  /*
235  * ------- check command line arguments and set args ------------------
236  */
237 
238  strcpy(gridflag, "s"); /* says: use std as default output QC field */
239  if ((check_usage(argc, argv)) != 0) pexit("insufficient args provided");
240 
241  strcpy(infileRT, argv[1]);
242  strcpy(infileCLM, argv[2]);
243  strcpy(outfile, argv[3]);
244  strcpy(monthstr, argv[4]);
245 
246  if (!strcmp(lowcase(argv[5]), "ozone"))
247  pexit("OZONE parameter type not supported by this program.");
248 
249  if (!strcmp(lowcase(argv[5]), "z_wind")) {
250  loval = loZ_WIND;
251  hival = hiZ_WIND;
252  } else if (!strcmp(lowcase(argv[5]), "m_wind")) {
253  loval = loM_WIND;
254  hival = hiM_WIND;
255  } else if (!strcmp(lowcase(argv[5]), "press")) {
256  loval = loPRESS;
257  hival = hiPRESS;
258  } else if (!strcmp(lowcase(argv[5]), "rel_hum")) {
259  loval = loREL_HUM;
260  hival = hiREL_HUM;
261  } else if (!strcmp(lowcase(argv[5]), "p_water")) {
262  loval = loP_WATER;
263  hival = hiP_WATER;
264  } else
265  pexit(
266  "parameter must be 'z_wind', 'm_wind', 'press', 'rel_hum' or 'p_water'.");
267 
268  strcpy(vgroupname, argv[5]);
269 
270  sscanf(argv[6], "%f", &stdlimit1);
271  sscanf(argv[7], "%f", &stdlimit2);
272  sscanf(argv[8], "%f", &stdlimit3);
273  sscanf(argv[9], "%d", &maxmissing);
274  if (argc >= 11) sscanf(argv[10], "%f", &loval);
275  if (argc >= 12) sscanf(argv[11], "%f", &hival);
276  if (argc >= 13) sscanf(argv[12], "%d", &outmax);
277  if (argc >= 14) {
278  strncpy(gridflag, argv[14], 1);
279  gridflag[1] = '\0';
280  }
281  if (argc >= 15) ifileflag = atoi(argv[15]);
282 
283 
284  /*
285  * ------- Read Z/M_WIND, PRESS, REL_HUM or OZONE real-time array files ---------
286  */
287 
288  if (ifileflag == CLMfile) {
289  strcpy(vgname, monthstr);
290  strcpy(sdsname, vgroupname);
291  strcat(sdsname, "_mean");
292  } else {
293  strcpy(vgname, "Geophysical Data");
294  strcpy(sdsname, vgroupname);
295  }
296  /*
297  * Read the size of the NRT field and set the size here
298  */
299  if (rd_size(infileRT, (int*) &shape_nrt[1], (int*) &shape_nrt[0]) != 0) {
300  pexit("metqc: Unable to read the data field size");
301  }
302  /*
303  * allocate the nrt-size arrays here
304  * RT - met field
305  * CLMAVG - mean climatology
306  * CLMSTD - Standard deviation of observations around the mean
307  * QC - output QC field
308  */
309  rank = 2;
310  array_size = shape_nrt[0] * shape_nrt[1];
311 
312  if ((float_SDSdataRT =
313  (float32 *) malloc(sizeof (float32) * array_size)) == NULL)
314  pexit("malloc float_SDSdataRT");
315 
316  if ((float_SDSdataCLMAVG =
317  (float32 *) malloc(sizeof (float32) * array_size)) == NULL)
318  pexit("malloc float_SDSdataCLMAVG");
319 
320  if ((float_SDSdataCLMSTD =
321  (float32 *) malloc(sizeof (float32) * array_size)) == NULL)
322  pexit("malloc float_SDSdataCLMSTD");
323 
324  if ((float_SDSdataQC =
325  (float32 *) malloc(sizeof (float32) * array_size)) == NULL)
326  pexit("malloc float_SDSdataQC");
327  /*
328  * Read Z/M_WIND, PRESS, REL_HUM, P_WATER or OZONE real-time array files
329  */
330 
331  if ((rdsds(infileRT, vgname, sdsname, inShape,
332  float_SDSdataRT)) != 0) pexit("rdsds RT");
333 
334  if ((inShape[0] != shape_nrt[0]) || (inShape[1] != shape_nrt[1])) {
335  printf("inShape[0] %d shape_nrt[0] %d inShape[1] %d shape_nrt[1] %d\n",
336  inShape[0], shape_nrt[0], inShape[1], shape_nrt[1]);
337  pexit("real-time dimensions not matching expected");
338  }
339 
340  /*
341  * ------- Determine appropriate climatology month (SDS) to match ------
342  * real time file. Get the average and std.dev. SDSs.
343  */
344 
345  /*
346  * Read the size of the CLM field and set the size here
347  */
348  if (rd_size(infileCLM, (int*) &shape_clm[1], (int*) &shape_clm[0]) != 0) {
349  pexit("metqc: Unable to read the climatology data field size");
350  }
351  /*
352  * allocate the space
353  */
354  if ((c_avg =
355  (float32 *) malloc(sizeof (float32) * shape_clm[0] * shape_clm[1]))
356  == NULL) {
357  pexit("malloc float_SDSdataCLMAVG");
358  }
359  if ((c_std =
360  (float32 *) malloc(sizeof (float32) * shape_clm[0] * shape_clm[1]))
361  == NULL) {
362  pexit("malloc float_SDSdataCLMAVG");
363  }
364 
365  strcpy(vgname, monthstr);
366  strcpy(sdsname, vgroupname);
367  strcat(sdsname, "_mean");
368 
369  if ((rdsds(infileCLM, vgname, sdsname, inShape,
370  c_avg)) != 0) pexit("rdsds CLMAVG");
371 
372  if ((inShape[0] != shape_clm[0]) || (inShape[1] != shape_clm[1])) {
373  printf("inShape[0] %d shape_clm[0] %d inShape[1] %d shape_clm[1] %d\n",
374  inShape[0], shape_clm[0], inShape[1], shape_clm[1]);
375  pexit("clim avg dimensions not matching expected");
376  }
377 
378  strcpy(sdsname, vgroupname);
379  strcat(sdsname, "_std_dev");
380 
381  if ((rdsds(infileCLM, vgname, sdsname, inShape,
382  c_std)) != 0) pexit("rdsds CLMSTD");
383 
384  if ((inShape[0] != shape_clm[0]) || (inShape[1] != shape_clm[1])) {
385  printf("inShape[0] %d shape_clm[0] %d inShape[1] %d shape_clm[1] %d\n",
386  inShape[0], shape_clm[0], inShape[1], shape_clm[1]);
387  pexit("clim std dimensions not matching expected");
388  }
389 
390  /*
391  l = 0;
392  for (i = 0; i < shape_nrt[0]; i++) {
393  printf ("\n");
394  for (j = 0; j < shape_nrt[1]; j++) {
395  printf ("%f ", float_SDSdataRT[l]);
396  l++;
397  }
398  }
399  */
400 
401  /*
402  * reconcile the climatology array size to that of the met field
403  */
404  printf("NRT field size is - pixels: %d, lines: %d\n",
405  shape_nrt[1], shape_nrt[0]);
406  if (shape_clm[0] != shape_nrt[0] || shape_clm[1] != shape_nrt[1]) {
407  printf("NOTE: Climatology field size is different\n");
408  printf(" Pixels: %d, lines: %d\n", shape_clm[1], shape_clm[0]);
409  printf(" Resizing climatology to match NRT\n");
410  }
411 
412  if ((shape_clm[0] <= 0) || (shape_clm[1] <= 0) ||
413  (shape_nrt[0] <= 0) || (shape_nrt[1] <= 0)) {
414  pexit("metqc: one of shape_clm, shape_nrt dimensions <= 0!");
415  }
416  if (resize_2d(c_avg, shape_clm[1], shape_clm[0],
417  shape_nrt[1], shape_nrt[0], float_SDSdataCLMAVG) != 0) {
418  pexit("metqc: resize_2d problem for CLMAVG, exiting");
419  }
420 
421  if (resize_2d(c_std, shape_clm[1], shape_clm[0],
422  shape_nrt[1], shape_nrt[0], float_SDSdataCLMSTD) != 0) {
423  pexit("metqc: resize_2d problem for CLMSTD, exiting");
424  }
425  free(c_avg);
426  free(c_std);
427 
428  /*
429  * ------- Compute variance of real-time from climatology -----------
430  * and tally #0s (and/or missing), #+ & - 1,2,3 std dev
431  * for writing to file for mailing.
432  */
433 
434  p = 0;
435  missing = 0;
436  locnt = 0;
437  hicnt = 0;
438  rtmiss = 0;
439  neg1cnt = 0;
440  neg2cnt = 0;
441  neg3cnt = 0;
442  pos1cnt = 0;
443  pos2cnt = 0;
444  pos3cnt = 0;
445 
446  for (i = 0; i < shape_nrt[0]; i++) {
447  for (j = 0; j < shape_nrt[1]; j++) {
448  float_SDSdataQC[p] = 0.0; /* initialize each point */
449 
450  /* pt. is missing, NRT missing, a MIN val, and counted as out of
451  lower range */
452  if ((float_SDSdataRT[p] <= VALIDMIN) ||
453  (float_SDSdataCLMAVG[p] <= VALIDMIN)) {
454  missing++;
455  if (float_SDSdataRT[p] <= VALIDMIN) rtmiss++;
456  if (float_SDSdataRT[p] < minval) minval = float_SDSdataRT[p];
457  if (float_SDSdataRT[p] < loval) locnt++;
458  } else {
459  if ((!strcmp(gridflag, "d")) || (!strcmp(gridflag, "D"))) {
460  float_SDSdataQC[p] =
461  (float32) float_SDSdataRT[p] - float_SDSdataCLMAVG[p];
462  } else {
463  if (float_SDSdataCLMSTD[p] > 0)
464  float_SDSdataQC[p] = (float32)
465  (float_SDSdataRT[p] - float_SDSdataCLMAVG[p]) /
466  float_SDSdataCLMSTD[p];
467  }
468 
469  /* find min and max of all points */
470  if (float_SDSdataRT[p] < minval) minval = float_SDSdataRT[p];
471  if (float_SDSdataRT[p] > maxval) maxval = float_SDSdataRT[p];
472 
473  /* sum up points outside lo/hi range (LO adds to missing counts)*/
474  if (float_SDSdataRT[p] < loval) locnt++;
475  if (float_SDSdataRT[p] > hival) hicnt++;
476 
477  if (float_SDSdataQC[p] < -1.0) neg1cnt++;
478  if (float_SDSdataQC[p] < -2.0) neg2cnt++;
479  if (float_SDSdataQC[p] < -3.0) neg3cnt++;
480 
481  if (float_SDSdataQC[p] > 1.0) pos1cnt++;
482  if (float_SDSdataQC[p] > 2.0) pos2cnt++;
483  if (float_SDSdataQC[p] > 3.0) pos3cnt++;
484  }
485  /*
486  if ((j > 100) && (j < 150)) {
487  printf("QC [%d][%d]: %f\n", i,j,float_SDSdataQC[p]);
488  printf("RT [%d][%d]: %f\n", i,j,float_SDSdataRT[p]);
489  printf("AVG [%d][%d]: %f\n", i,j,float_SDSdataCLMAVG[p]);
490  printf("STD [%d][%d]: %f\n", i,j,float_SDSdataCLMSTD[p]);
491  }
492  printf("[%d][%d]: %f %f %f\n", i,j,float_SDSdataRT[p],
493  float_SDSdataCLMAVG[p], float_SDSdataCLMSTD[p]);
494  */
495  p++;
496  } /* for j */
497  } /* for i */
498 
499  totalpts = array_size - missing;
500 
501  free(float_SDSdataRT);
502  free(float_SDSdataCLMAVG);
503  free(float_SDSdataCLMSTD);
504 
505 #if 0
506  p = 0;
507  for (i = 0; i < shape_nrt[0]; i++) {
508  for (j = 0; j < shape_nrt[1]; j++) {
509  float_SDSdataQC[p] = 0.0; /* initialize each point */
510  p++;
511  } /* for j */
512  } /* for i */
513 #endif
514 
515  /*
516  * ----------------- Write QC SDS ----------------------------
517  */
518 
519  /*
520  * Create HDF file
521  */
522 
523 
524  if ((startHDF(outfile, &sdfid, &fid, DFACC_CREATE)) != 0)
525  pexit("Fatal error starting output HDF file");
526 
527  /*
528  * Create grid structure
529  */
530 
531  /* gridid = setupGrid(fid, VGROUPCLASS, vgroupname); */
532  gridid = setupGrid(fid, vgroupname);
533 
534  /*
535  * Write geometry Vdata, get ref, and add to grid Vgroup (geomid not used)
536  */
537 
538  if ((geomid = writeGeom(fid, gridid, GEOMNAME, BIN_METH, REGISTRATION,
540  MAX_WEST, MAX_EAST)) == ERROR)
541  pexit("Fatal error writing geometry");
542 
543  /*
544  * Write SDS grid
545  */
546 
547  strcpy(datalabel, "QC array");
548  datatype = DFNT_FLOAT;
549  dataattr = "UNITS";
550  dataunit = "std dev diff";
551 
552  if ((sdsid = wrtsds(sdfid, rank, shape_nrt, datatype, datalabel,
553  float_SDSdataQC)) < 0) pexit("main wrtsds");
554 
555  free(float_SDSdataQC);
556 
557  /*
558  * set SDS attribute
559  */
560 
561  if ((result = addAttr(sdsid, dataattr, DFNT_CHAR, dataunit)) != 0)
562  pexit("addAttr");
563 
564  /*
565  * add SDS to Vgroup and deattach SDS
566  */
567 
568  if ((result = setSDSref(sdsid, gridid)) != 0) pexit("setSDSref");
569 
570  /*
571  * deattach HDF grid
572  */
573 
574  deattachHDFgrid(gridid);
575 
576  /*
577  * close HDF structures
578  */
579 
580  if ((result = closeHDFstructs(sdfid, fid)) != 0) pexit("closeHDFstructs");
581 
582  /*
583  * ----------------- Print stats to standard output -----------
584  */
585 
586  /* printf("gridflag [%s]\n",gridflag); */
587 
588  if (!strcmp(gridflag, "s")) {
589  printf("\n");
590  printf("-------------------------------------------------------------\n");
591  printf("Results of comparison of real-time and climatological files:\n");
592  printf("%s\n%s\n", infileRT, infileCLM);
593  printf("Month: %s\t\tParameter: %s\n", monthstr, argv[5]);
594  printf("Thresholds: %8.3f %8.3f %8.3f Max Missings: %d",
595  stdlimit1, stdlimit2, stdlimit3, maxmissing);
596  printf("\n");
597  printf("Minimum value: %8.3f Maximum: %8.3f\n", minval, maxval);
598 
599  printf("Total # non-missing values: %6d\n", totalpts);
600  printf("Total # values <%8.3f: %d >%8.3f: %d allowed: %d",
601  loval, locnt, hival, hicnt, outmax);
602 
603  /* if (locnt >= outmax) failed = 1; lo points out of range exceeded */
604  /* if (hicnt >= outmax) failed = 1; hi points out of range exceeded */
605  /*
606  * WDR if fail in either case, append a set of astrisks
607  */
608  if (locnt >= outmax || hicnt >= outmax) {
609  failed = 1;
610  printf(" ***\n");
611  } else {
612  printf("\n");
613  }
614 
615  printf("\n");
616  printf("Total # points/percentage < -1 STD: %6d (%5.2f percent)\n",
617  neg1cnt, (float) neg1cnt / totalpts * 100.0);
618  printf("Total # points/percentage +/- 1 STD: %6d (%5.2f percent)",
619  totalpts - (neg1cnt + pos1cnt),
620  (float) (totalpts - (pos1cnt + neg1cnt)) / totalpts * 100.0);
621 
622  if (((float) (totalpts - (pos1cnt + neg1cnt)) / totalpts * 100.0) <
623  stdlimit1) {
624  failed = 1;
625  printf(" ***\n");
626  } else {
627  printf("\n");
628  }
629 
630  printf("Total # points/percentage > 1 STD: %6d (%5.2f percent)\n",
631  pos1cnt, (float) pos1cnt / totalpts * 100.0);
632  printf("\n");
633 
634  printf("Total # points/percentage < -2 STD: %6d (%5.2f percent)\n",
635  neg2cnt, (float) neg2cnt / totalpts * 100.0);
636  printf("Total # points/percentage +/- 2 STD: %6d (%5.2f percent)",
637  totalpts - (neg2cnt + pos2cnt),
638  (float) (totalpts - (pos2cnt + neg2cnt)) / totalpts * 100.0);
639 
640  if (((float) (totalpts - (pos2cnt + neg2cnt)) / totalpts * 100.0) <
641  stdlimit2) {
642  failed = 1;
643  printf(" ***\n");
644  } else {
645  printf("\n");
646  }
647 
648  printf("Total # points/percentage > 2 STD: %6d (%5.2f percent)\n",
649  pos2cnt, (float) pos2cnt / totalpts * 100.0);
650  printf("\n");
651 
652  printf("Total # points/percentage < -3 STD: %6d (%5.2f percent)\n",
653  neg3cnt, (float) neg3cnt / totalpts * 100.0);
654  printf("Total # points/percentage +/- 3 STD: %6d (%5.2f percent)",
655  totalpts - (neg3cnt + pos3cnt),
656  (float) (totalpts - (pos3cnt + neg3cnt)) / totalpts * 100.0);
657 
658  if (((float) (totalpts - (pos3cnt + neg3cnt)) / totalpts * 100.0) <
659  stdlimit3) {
660  failed = 1;
661  printf(" ***\n");
662  } else {
663  printf("\n");
664  }
665 
666  printf("Total # points/percentage > 3 STD: %6d (%5.2f percent)\n",
667  pos3cnt, (float) pos3cnt / totalpts * 100.0);
668  printf("\n");
669 
670  printf("Total # missing values: %6d\n", missing);
671  printf("Total # missing real-time: %6d", rtmiss);
672  if (rtmiss > maxmissing) {
673  failed = 1;
674  printf(" ***\n");
675  } else {
676  printf("\n");
677  }
678  printf("-------------------------------------------------------------\n");
679  printf("\n\n");
680 
681  }
682 
683  /* set exit value to reflect threshold checks */
684 
685  if (failed) {
686  printf("Threshold Status: FAILED\n");
687  return (FAILURE);
688  } else {
689  printf("Threshold Status: SUCCESS\n");
690  return (SUCCESS);
691  }
692 } /* main */
693 
694 /*****************************************************************
695  *
696  * check user parameters and show example if not all parms given
697  *
698  *****************************************************************/
699 
700 int8 check_usage(int argc, char *argv[]) {
701  if (argc < 9) {
702  printf("\n\nUsage:\n");
703  printf("\t%s <file><file><outfile><monthstr><param><t1><t2><t2><maxmiss><lo><hi><outmax>[diff][type] \n", argv[0]);
704  printf("\nWhere:\n");
705  printf("\tfile: Real-time file to process\n");
706  printf("\tfile: Climatology file\n");
707  printf("\toutfile: Output QC file\n");
708  printf("\tmonthstr: Month in string form (i.e., January)\n");
709  printf("\tparam: Parameter to run: z_wind m_wind press rel_hum p_water\n");
710  printf("\tt1: Threshold percent of pts w/in 1 STD DEV of clim\n");
711  printf("\tt2: Threshold percent of pts w/in 2 STD DEV of clim\n");
712  printf("\tt3: Threshold percent of pts w/in 3 STD DEV of clim\n");
713  printf("\tmaxmiss: Max num of missing NRT points permitted\n");
714  printf("\tlo: Lowest allowed value in NRT file\n");
715  printf("\thi: Highest allowed value in NRT file\n");
716  printf("\tlo: Maximum # of NRT points allowed outside of lo/hi before returning an error flag\n");
717  printf("\t [optional] parameters follow. Preceeding args \n");
718  printf("\t are required for subsequent ones used\n");
719  printf("\tdiff: [optional] Enter 'd' to see a simple difference output\n");
720  printf("\t grid rather than the default STD variance 's'\n");
721  printf("\t Difference calculations do not product reports\n");
722  printf("\ttype [optional] Enter 1 if NRT file is actually a CLM file\n");
723  printf("\t This will allow the program to read the CLM\n");
724  printf("\t as of test of CLM to itself\n");
725  printf("\n");
726  return (ERROR);
727  }
728  return 0;
729 }
struct annotation * annot
Definition: metqc.c:161
int32_t setupGrid(int32_t fid, char *grpname)
Definition: ANCroutines.c:51
#define SUCCESS
Definition: ObpgReadGrid.h:15
int j
Definition: decode_rs.h:73
#define CLMfile
Definition: metqc.c:159
char * lowcase(char *instr)
Definition: lowcase.c:10
int addAttr(int32_t sdsid, char *dataattr, int32_t datatype, char *dataunit)
Definition: ANCroutines.c:222
int8 check_usage(int argc, char *argv[])
Definition: metqc.c:700
int main(int argc, char *argv[])
Definition: metqc.c:163
#define NULL
Definition: decode_rs.h:63
int rd_size(char *file, int *npix, int *nlin)
Definition: rd_size.c:4
#define MAX_SOUTH
Definition: metqc.c:154
#define HSIZE
Definition: metqc.c:152
#define MAX_EAST
Definition: metqc.c:156
int resize_2d(float *in_arr, int inpix, int inlin, int outpix, int outlin, float *out_arr)
Definition: resize_2d.c:1
#define VALIDMIN
Definition: metqc.c:158
#define BIN_METH
Definition: metqc.c:147
int32_t wrtsds(int32_t sdfid, int rank, int32_t *shape, int32_t datatype, char *datalabel, void *data)
int deattachHDFgrid(int32_t gridid)
Definition: ANCroutines.c:267
#define VSIZE
Definition: metqc.c:151
int closeHDFstructs(int32_t sdfid, int32_t fid)
Definition: ANCroutines.c:281
void pexit(char *string)
Definition: pexit.c:10
int32_t writeGeom(int32_t fid, int32_t gridid, char *geomname, int32_t bin_meth, int32_t registration, float vsize, float hsize, float max_north, float max_south, float max_west, float max_east)
Definition: ANCroutines.c:92
#define FAILURE
Definition: ancil.h:25
Extra metadata that will be written to the HDF4 file l2prod rank
PARAM_TYPE_NONE Default value No parameter is buried in the product name name_prefix is case insensitive string compared to the product name PARAM_TYPE_VIS_WAVE The visible wavelength bands from the sensor are buried in the product name The product name is compared by appending and name_suffix ie aph_412_giop where prod_ix will be set to PARAM_TYPE_IR_WAVE same search method as PARAM_TYPE_VIS_WAVE except only wavelength above are looped through but prod_ix is still based ie aph_2_giop for the second and prod_ix set to PARAM_TYPE_INT name_prefix is compared with the beginning of the product name If name_suffix is not empty the it must match the end of the product name The characters right after the prefix are read as an integer and prod_ix is set to that number strncpy(l2prod->name_prefix, "myprod", UNITLEN)
#define REGISTRATION
Definition: metqc.c:148
int setSDSref(int32_t sdsid, int32_t gridid)
Definition: ANCroutines.c:245
#define MAXNAMELNG
Definition: ancil.h:43
int i
Definition: decode_rs.h:71
#define GEOMNAME
Definition: ancil.h:44
#define MAX_NORTH
Definition: metqc.c:153
How many dimensions is the output array Default is Not sure if anything above will work correctly strcpy(l2prod->title, "no title yet")
#define MAX_WEST
Definition: metqc.c:155
int rdsds(char *filename, char *vgname, char *sdsname, int32_t *dimsizes, void *inData)
float p[MODELMAX]
Definition: atrem_corl1.h:131
int startHDF(char *outfile, int32_t *sdfid, int32_t *fid, int32_t mode)
Definition: ANCroutines.c:27
#define ERROR
Definition: ancil.h:24