MPTRAC
met_lapse.c
Go to the documentation of this file.
1/*
2 This file is part of MPTRAC.
3
4 MPTRAC is free software: you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation, either version 3 of the License, or
7 (at your option) any later version.
8
9 MPTRAC is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
13
14 You should have received a copy of the GNU General Public License
15 along with MPTRAC. If not, see <http://www.gnu.org/licenses/>.
16
17 Copyright (C) 2013-2026 Forschungszentrum Juelich GmbH
18*/
19
25#include "mptrac.h"
26
27/* ------------------------------------------------------------
28 Dimensions...
29 ------------------------------------------------------------ */
30
32#define LAPSEMIN -20.0
33
35#define DLAPSE 0.1
36
38#define IDXMAX 400
39
40/* ------------------------------------------------------------
41 Functions...
42 ------------------------------------------------------------ */
43
45void usage(
46 void);
47
48/* ------------------------------------------------------------
49 Main...
50 ------------------------------------------------------------ */
51
52int main(
53 int argc,
54 char *argv[]) {
55
56 ctl_t ctl;
57
58 clim_t *clim;
59
60 met_t *met;
61
62 dd_t *dd;
63
64 FILE *out;
65
66 static double p2[1000], t[1000], t2[1000], z[1000], z2[1000], lat_mean,
67 z_mean;
68
69 static int hist_max[1000], hist_min[1000], hist_mean[1000], hist_sig[1000],
70 nhist_max, nhist_min, nhist_mean, nhist_sig, np;
71
72 /* Allocate... */
73 mptrac_alloc(NULL, NULL, &clim, &met, NULL, NULL, NULL, &dd);
74
75 /* Print usage information... */
76 USAGE;
77
78 /* Check arguments... */
79 if (argc < 4)
80 ERRMSG("Missing or invalid command-line arguments.\n\n"
81 "Usage: met_lapse <ctl> <lapse.tab> <met0> [<met1> ...]\n\n"
82 "Use -h for full help.");
83
84 /* Read control parameters... */
85 mptrac_read_ctl(argv[1], argc, argv, &ctl);
86 const int dz =
87 (int) scan_ctl(argv[1], argc, argv, "LAPSE_DZ", -1, "20", NULL);
88 const double lat0 =
89 (int) scan_ctl(argv[1], argc, argv, "LAPSE_LAT0", -1, "-90", NULL);
90 const double lat1 =
91 (int) scan_ctl(argv[1], argc, argv, "LAPSE_LAT1", -1, "90", NULL);
92 const double z0 =
93 (int) scan_ctl(argv[1], argc, argv, "LAPSE_Z0", -1, "0", NULL);
94 const double z1 =
95 (int) scan_ctl(argv[1], argc, argv, "LAPSE_Z1", -1, "100", NULL);
96 const int intpol =
97 (int) scan_ctl(argv[1], argc, argv, "LAPSE_INTPOL", -1, "1", NULL);
98
99 /* Read climatological data... */
100 mptrac_read_clim(&ctl, clim);
101
102 /* Loop over files... */
103 for (int i = 3; i < argc; i++) {
104
105 /* Read meteorological data... */
106 if (!mptrac_read_met(argv[i], &ctl, clim, met, dd))
107 continue;
108
109 /* Get altitude and pressure profiles... */
110 for (int iz = 0; iz < met->np; iz++)
111 z[iz] = Z(met->p[iz]);
112 for (int iz = 0; iz <= 250; iz++) {
113 z2[iz] = 0.0 + 0.1 * iz;
114 p2[iz] = P(z2[iz]);
115 }
116
117 /* Loop over grid points... */
118 for (int ix = 0; ix < met->nx; ix++)
119 for (int iy = 0; iy < met->ny; iy++) {
120
121 /* Check latitude range... */
122 if (met->lat[iy] < lat0 || met->lat[iy] > lat1)
123 continue;
124
125 /* Interpolate temperature profile... */
126 for (int iz = 0; iz < met->np; iz++)
127 t[iz] = met->t[ix][iy][iz];
128 if (intpol == 1)
129 spline(z, t, met->np, z2, t2, 251, ctl.met_tropo_spline);
130 else
131 for (int iz = 0; iz <= 250; iz++) {
132 int idx = locate_irr(z, met->np, z2[iz]);
133 t2[iz] = LIN(z[idx], t[idx], z[idx + 1], t[idx + 1], z2[iz]);
134 }
135
136 /* Loop over vertical levels... */
137 for (int iz = 0; iz <= 250; iz++) {
138
139 /* Check height range... */
140 if (z2[iz] < z0 || z2[iz] > z1)
141 continue;
142
143 /* Check surface pressure... */
144 if (p2[iz] > met->ps[ix][iy])
145 continue;
146
147 /* Get mean latitude and height... */
148 lat_mean += met->lat[iy];
149 z_mean += z2[iz];
150 np++;
151
152 /* Get lapse rates within a vertical layer... */
153 int nlapse = 0;
154 double lapse_max = -1e99, lapse_min = 1e99, lapse_mean =
155 0, lapse_sig = 0;
156 for (int iz2 = iz + 1; iz2 <= iz + dz; iz2++) {
157 lapse_max =
158 MAX(LAPSE(p2[iz], t2[iz], p2[iz2], t2[iz2]), lapse_max);
159 lapse_min =
160 MIN(LAPSE(p2[iz], t2[iz], p2[iz2], t2[iz2]), lapse_min);
161 lapse_mean += LAPSE(p2[iz], t2[iz], p2[iz2], t2[iz2]);
162 lapse_sig += SQR(LAPSE(p2[iz], t2[iz], p2[iz2], t2[iz2]));
163 nlapse++;
164 }
165 lapse_mean /= nlapse;
166 lapse_sig = sqrt(MAX(lapse_sig / nlapse - SQR(lapse_mean), 0));
167
168 /* Get histograms... */
169 int idx = (int) ((lapse_max - LAPSEMIN) / DLAPSE);
170 if (idx >= 0 && idx < IDXMAX) {
171 hist_max[idx]++;
172 nhist_max++;
173 }
174
175 idx = (int) ((lapse_min - LAPSEMIN) / DLAPSE);
176 if (idx >= 0 && idx < IDXMAX) {
177 hist_min[idx]++;
178 nhist_min++;
179 }
180
181 idx = (int) ((lapse_mean - LAPSEMIN) / DLAPSE);
182 if (idx >= 0 && idx < IDXMAX) {
183 hist_mean[idx]++;
184 nhist_mean++;
185 }
186
187 idx = (int) ((lapse_sig - LAPSEMIN) / DLAPSE);
188 if (idx >= 0 && idx < IDXMAX) {
189 hist_sig[idx]++;
190 nhist_sig++;
191 }
192 }
193 }
194 }
195
196 /* Create output file... */
197 LOG(1, "Write lapse rate data: %s", argv[2]);
198 if (!(out = fopen(argv[2], "w")))
199 ERRMSG("Cannot create file!");
200
201 /* Write header... */
202 fprintf(out,
203 "# $1 = mean altitude [km]\n"
204 "# $2 = mean latitude [deg]\n"
205 "# $3 = lapse rate [K/km]\n"
206 "# $4 = counts of maxima per bin\n"
207 "# $5 = total number of maxima\n"
208 "# $6 = normalized frequency of maxima\n"
209 "# $7 = counts of minima per bin\n"
210 "# $8 = total number of minima\n"
211 "# $9 = normalized frequency of minima\n"
212 "# $10 = counts of means per bin\n"
213 "# $11 = total number of means\n"
214 "# $12 = normalized frequency of means\n"
215 "# $13 = counts of sigmas per bin\n"
216 "# $14 = total number of sigmas\n"
217 "# $15 = normalized frequency of sigmas\n\n");
218
219 /* Write data... */
220 double nmax_max = 0, nmax_min = 0, nmax_mean = 0, nmax_sig = 0;
221 for (int idx = 0; idx < IDXMAX; idx++) {
222 nmax_max = MAX(hist_max[idx], nmax_max);
223 nmax_min = MAX(hist_min[idx], nmax_min);
224 nmax_mean = MAX(hist_mean[idx], nmax_mean);
225 nmax_sig = MAX(hist_sig[idx], nmax_sig);
226 }
227 for (int idx = 0; idx < IDXMAX; idx++)
228 fprintf(out,
229 "%g %g %g %d %d %g %d %d %g %d %d %g %d %d %g\n",
230 z_mean / np, lat_mean / np, (idx + .5) * DLAPSE + LAPSEMIN,
231 hist_max[idx], nhist_max,
232 (double) hist_max[idx] / (double) nmax_max, hist_min[idx],
233 nhist_min, (double) hist_min[idx] / (double) nmax_min,
234 hist_mean[idx], nhist_mean,
235 (double) hist_mean[idx] / (double) nmax_mean, hist_sig[idx],
236 nhist_sig, (double) hist_sig[idx] / (double) nmax_sig);
237
238 /* Close file... */
239 fclose(out);
240
241 /* Free... */
242 mptrac_free(NULL, NULL, clim, met, NULL, NULL, NULL, dd);
243
244 return EXIT_SUCCESS;
245}
246
247/*****************************************************************************/
248
250void usage(
251 void) {
252
253 printf("\nMPTRAC met_lapse tool.\n\n");
254 printf("Calculate lapse-rate statistics from meteorological data.\n");
255 printf("\n");
256 printf("Usage:\n");
257 printf(" met_lapse <ctl> <lapse.tab> <met0> [<met1> ...]\n");
258 printf("\n");
259 printf("Arguments:\n");
260 printf(" <ctl> Control file.\n");
261 printf(" <lapse.tab> Output table for lapse-rate statistics.\n");
262 printf(" <met*> Meteorological input files.\n");
263 printf("\nFurther information:\n");
264 printf(" Manual: https://slcs-jsc.github.io/mptrac/\n");
265}
int main(int argc, char *argv[])
Definition: met_lapse.c:52
#define LAPSEMIN
Lapse rate minimum [K/km].
Definition: met_lapse.c:32
#define IDXMAX
Maximum number of histogram bins.
Definition: met_lapse.c:38
#define DLAPSE
Lapse rate bin size [K/km].
Definition: met_lapse.c:35
void usage(void)
Print command-line help.
Definition: met_lapse.c:250
int locate_irr(const double *xx, const int n, const double x)
Locate the index of the interval containing a given value in a sorted array.
Definition: mptrac.c:3495
void mptrac_free(ctl_t *ctl, cache_t *cache, clim_t *clim, met_t *met0, met_t *met1, atm_t *atm, depo_t *depo, dd_t *dd)
Frees memory resources allocated for MPTRAC.
Definition: mptrac.c:6397
void spline(const double *x, const double *y, const int n, const double *x2, double *y2, const int n2, const int method)
Performs spline interpolation or linear interpolation.
Definition: mptrac.c:12567
double scan_ctl(const char *filename, int argc, char *argv[], const char *varname, const int arridx, const char *defvalue, char *value)
Scans a control file or command-line arguments for a specified variable.
Definition: mptrac.c:12462
void mptrac_read_clim(const ctl_t *ctl, clim_t *clim)
Reads various climatological data and populates the given climatology structure.
Definition: mptrac.c:6683
void mptrac_alloc(ctl_t **ctl, cache_t **cache, clim_t **clim, met_t **met0, met_t **met1, atm_t **atm, depo_t **depo, dd_t **dd)
Allocates and initializes memory resources for MPTRAC.
Definition: mptrac.c:6314
int mptrac_read_met(const char *filename, const ctl_t *ctl, const clim_t *clim, met_t *met, dd_t *dd)
Reads meteorological data from a file, supporting multiple formats and MPI broadcasting.
Definition: mptrac.c:7767
void mptrac_read_ctl(const char *filename, int argc, char *argv[], ctl_t *ctl)
Reads control parameters from a configuration file and populates the given structure.
Definition: mptrac.c:6743
MPTRAC library declarations.
#define LAPSE(p1, t1, p2, t2)
Calculate lapse rate.
Definition: mptrac.h:1331
#define MIN(a, b)
Macro to determine the minimum of two values.
Definition: mptrac.h:1478
#define ERRMSG(...)
Print an error message with contextual information and terminate the program.
Definition: mptrac.h:2405
#define USAGE
Print usage information on -h or --help.
Definition: mptrac.h:2212
#define Z(p)
Convert pressure to altitude.
Definition: mptrac.h:2242
#define P(z)
Compute pressure at given altitude.
Definition: mptrac.h:1783
#define SQR(x)
Compute the square of a value.
Definition: mptrac.h:2036
#define LOG(level,...)
Print a log message with a specified logging level.
Definition: mptrac.h:2335
#define LIN(x0, y0, x1, y1, x)
Linear interpolation.
Definition: mptrac.h:1350
#define MAX(a, b)
Macro to determine the maximum of two values.
Definition: mptrac.h:1377
Climatological data.
Definition: mptrac.h:3787
Control parameters.
Definition: mptrac.h:2493
int met_tropo_spline
Tropopause interpolation method (0=linear, 1=spline).
Definition: mptrac.h:2999
Domain decomposition data structure.
Definition: mptrac.h:4023
Meteo data structure.
Definition: mptrac.h:3846
int nx
Number of longitudes.
Definition: mptrac.h:3855
int ny
Number of latitudes.
Definition: mptrac.h:3858
float ps[EX][EY]
Surface pressure [hPa].
Definition: mptrac.h:3888
int np
Number of pressure levels.
Definition: mptrac.h:3861
float t[EX][EY][EP]
Temperature [K].
Definition: mptrac.h:3963
double lat[EY]
Latitudes [deg].
Definition: mptrac.h:3870
double p[EP]
Pressure levels [hPa].
Definition: mptrac.h:3873