SDDS ToolKit Programs and Libraries for C and Python
Loading...
Searching...
No Matches
sddsinterpset.c File Reference

Detailed Description

Perform multiple interpolations on SDDS data sets.

This program reads an input SDDS file containing references to multiple data files. For each referenced data file, it performs interpolation based on specified parameters and writes the results to an output SDDS file. The interpolation behavior can be customized using various command-line options.

Usage

sddsinterpset [<input>] [<output>]
[-pipe=[input][,output]]
[-order=<number>]
[-verbose]
[-data=fileColumn=<colName>,interpolate=<colName>,functionof=<colName>,column=<colName> | atValue=<value>]
[-majorOrder=row|column]
[-belowRange={value=<value>|skip|saturate|extrapolate|wrap}[,{abort|warn}]]
[-aboveRange={value=<value>|skip|saturate|extrapolate|wrap}[,{abort|warn}]]
[-threads=<number>]
double interpolate(double *f, double *x, int64_t n, double xo, OUTRANGE_CONTROL *belowRange, OUTRANGE_CONTROL *aboveRange, long order, unsigned long *returnCode, long M)
Performs interpolation with range control options.
Definition interp.c:160

Options

Option Description
-pipe Use standard SDDS Toolkit pipe options for input and output.
-order Specify the order of the polynomials used for interpolation.
-verbose Print detailed processing messages.
-data Define data interpolation parameters.
-majorOrder Specify data ordering for output: row or column.
-belowRange Define behavior for out-of-range points below data range.
-aboveRange Define behavior for out-of-range points above data range.
-threads Number of referenced data files to read concurrently.

Incompatibilities

  • The column and atValue options within -data are mutually exclusive; only one can be specified per invocation.
License
This file is distributed under the terms of the Software License Agreement found in the file LICENSE included with this distribution.
Authors
H. Shang, R. Soliday, Xuesong Jiao, M. Borland

Definition in file sddsinterpset.c.

#include "mdb.h"
#include "SDDS.h"
#include "scan.h"
#include "SDDSutils.h"
#include <ctype.h>

Go to the source code of this file.

Functions

long checkMonotonicity (double *indepValue, int64_t rows)
 
void freedatacontrol (DATA_CONTROL *data_control, long dataControls)
 
static long interpolateDataFile (char *filename, DATA_CONTROL *control, double atValue, OUTRANGE_CONTROL *belowRange, OUTRANGE_CONTROL *aboveRange, long order, double *result, unsigned long *interpCode, char *errorMessage, long errorMessageSize)
 
int main (int argc, char **argv)
 

Function Documentation

◆ checkMonotonicity()

long checkMonotonicity ( double * indepValue,
int64_t rows )

Definition at line 654 of file sddsinterpset.c.

654 {
655 if (rows == 1)
656 return 1;
657
658 if (indepValue[rows - 1] > indepValue[0]) {
659 while (--rows > 0)
660 if (indepValue[rows] < indepValue[rows - 1])
661 return 0;
662 return 1;
663 } else {
664 while (--rows > 0)
665 if (indepValue[rows] > indepValue[rows - 1])
666 return 0;
667 return -1;
668 }
669}

◆ freedatacontrol()

void freedatacontrol ( DATA_CONTROL * data_control,
long dataControls )

Definition at line 671 of file sddsinterpset.c.

671 {
672 long i;
673 for (i = 0; i < dataControls; i++) {
674 free(data_control[i].interpCol);
675 free(data_control[i].funcOfCol);
676 free(data_control[i].fileColumn);
677 if (data_control[i].atCol)
678 free(data_control[i].atCol);
679 }
680 free(data_control);
681}

◆ interpolateDataFile()

static long interpolateDataFile ( char * filename,
DATA_CONTROL * control,
double atValue,
OUTRANGE_CONTROL * belowRange,
OUTRANGE_CONTROL * aboveRange,
long order,
double * result,
unsigned long * interpCode,
char * errorMessage,
long errorMessageSize )
static

Definition at line 579 of file sddsinterpset.c.

582 {
583 SDDS_DATASET SDDSdata;
584 double *indepValue = NULL, *depenValue = NULL;
585 int64_t datarows;
586 long monotonicity;
587 int initialized = 0;
588
589 if (!SDDS_InitializeInput(&SDDSdata, filename)) {
590 snprintf(errorMessage, errorMessageSize, "Error: unable to open input data file '%s'.", filename);
591 return 0;
592 }
593 initialized = 1;
594
595 if (SDDS_CheckColumn(&SDDSdata, control->interpCol, NULL, SDDS_ANY_NUMERIC_TYPE, NULL) != SDDS_CHECK_OKAY) {
596 snprintf(errorMessage, errorMessageSize, "Error: Column '%s' missing or invalid in file '%s'.",
597 control->interpCol, filename);
598 SDDS_Terminate(&SDDSdata);
599 return 0;
600 }
601 if (SDDS_CheckColumn(&SDDSdata, control->funcOfCol, NULL, SDDS_ANY_NUMERIC_TYPE, NULL) != SDDS_CHECK_OKAY) {
602 snprintf(errorMessage, errorMessageSize, "Error: Column '%s' missing or invalid in file '%s'.",
603 control->funcOfCol, filename);
604 SDDS_Terminate(&SDDSdata);
605 return 0;
606 }
607 if (SDDS_ReadPage(&SDDSdata) <= 0) {
608 snprintf(errorMessage, errorMessageSize, "Error: unable to read data page from file '%s'.", filename);
609 SDDS_Terminate(&SDDSdata);
610 return 0;
611 }
612 datarows = SDDS_CountRowsOfInterest(&SDDSdata);
613 if (datarows <= 0) {
614 snprintf(errorMessage, errorMessageSize, "Error: No data found in file '%s'.", filename);
615 SDDS_Terminate(&SDDSdata);
616 return 0;
617 }
618 if (!(indepValue = SDDS_GetColumnInDoubles(&SDDSdata, control->funcOfCol))) {
619 snprintf(errorMessage, errorMessageSize, "Error: problem getting column '%s' from file '%s'.",
620 control->funcOfCol, filename);
621 SDDS_Terminate(&SDDSdata);
622 return 0;
623 }
624 if (!(depenValue = SDDS_GetColumnInDoubles(&SDDSdata, control->interpCol))) {
625 snprintf(errorMessage, errorMessageSize, "Error: problem getting column '%s' from file '%s'.",
626 control->interpCol, filename);
627 free(indepValue);
628 SDDS_Terminate(&SDDSdata);
629 return 0;
630 }
631 if (initialized && !SDDS_Terminate(&SDDSdata)) {
632 snprintf(errorMessage, errorMessageSize, "Error: problem closing data file '%s'.", filename);
633 free(indepValue);
634 free(depenValue);
635 return 0;
636 }
637 initialized = 0;
638
639 if (!(monotonicity = checkMonotonicity(indepValue, datarows))) {
640 snprintf(errorMessage, errorMessageSize, "Error: Independent (%s) data in file '%s' is not monotonic.",
641 control->funcOfCol, filename);
642 free(indepValue);
643 free(depenValue);
644 return 0;
645 }
646
647 *result = interpolate(depenValue, indepValue, datarows, atValue,
648 belowRange, aboveRange, order, interpCode, monotonicity);
649 free(depenValue);
650 free(indepValue);
651 return 1;
652}
int64_t SDDS_CountRowsOfInterest(SDDS_DATASET *SDDS_dataset)
Counts the number of rows marked as "of interest" in the current data table.
double * SDDS_GetColumnInDoubles(SDDS_DATASET *SDDS_dataset, char *column_name)
Retrieves the data of a specified numerical column as an array of doubles, considering only rows mark...
int32_t SDDS_InitializeInput(SDDS_DATASET *SDDS_dataset, char *filename)
Definition SDDS_input.c:50
int32_t SDDS_Terminate(SDDS_DATASET *SDDS_dataset)
int32_t SDDS_ReadPage(SDDS_DATASET *SDDS_dataset)
int32_t SDDS_CheckColumn(SDDS_DATASET *SDDS_dataset, char *name, char *units, int32_t type, FILE *fp_message)
Checks if a column exists in the SDDS dataset with the specified name, units, and type.
#define SDDS_ANY_NUMERIC_TYPE
Special identifier used by SDDS_Check*() routines to accept any numeric type.
Definition SDDStypes.h:157

◆ main()

int main ( int argc,
char ** argv )

Definition at line 139 of file sddsinterpset.c.

139 {
140 int i_arg;
141 char *input = NULL, *output = NULL, **interpCol = NULL, **funcOf = NULL;
142 long order = 1, dataControls = 0, valid_option = 1;
143 //long verbose = 0;
144 SCANNED_ARG *s_arg;
145 OUTRANGE_CONTROL aboveRange, belowRange;
146 DATA_CONTROL *data_control = NULL;
147 unsigned long pipeFlags = 0, majorOrderFlag;
148 SDDS_DATASET SDDSdata, SDDSout, SDDSin;
149 double ***out_depenValue = NULL, atValue = 0;
150 int32_t **rowFlag = NULL;
151 long valid_data = 0, index, pages = 0;
152 int64_t *rows = NULL;
153 int64_t i, j, row;
154 short columnMajorOrder = -1;
155 int threads = 1;
156
158 argc = scanargs(&s_arg, argc, argv);
159 if (argc < 3) {
160 fprintf(stderr, "%s", USAGE);
161 exit(EXIT_FAILURE);
162 }
163
164 aboveRange.flags = belowRange.flags = OUTRANGE_SATURATE;
165
166 for (i_arg = 1; i_arg < argc; i_arg++) {
167 if (s_arg[i_arg].arg_type == OPTION) {
168 switch (match_string(s_arg[i_arg].list[0], option, N_OPTIONS, 0)) {
169 case CLO_MAJOR_ORDER:
170 majorOrderFlag = 0;
171 s_arg[i_arg].n_items--;
172 if (s_arg[i_arg].n_items > 0 &&
173 !scanItemList(&majorOrderFlag, s_arg[i_arg].list + 1, &s_arg[i_arg].n_items, 0,
174 "row", -1, NULL, 0, SDDS_ROW_MAJOR_ORDER,
175 "column", -1, NULL, 0, SDDS_COLUMN_MAJOR_ORDER, NULL)) {
176 SDDS_Bomb("invalid -majorOrder syntax/values");
177 }
178 if (majorOrderFlag & SDDS_COLUMN_MAJOR_ORDER)
179 columnMajorOrder = 1;
180 else if (majorOrderFlag & SDDS_ROW_MAJOR_ORDER)
181 columnMajorOrder = 0;
182 break;
183 case CLO_THREADS:
184 if (s_arg[i_arg].n_items != 2 ||
185 sscanf(s_arg[i_arg].list[1], "%d", &threads) != 1 ||
186 threads < 1) {
187 SDDS_Bomb("invalid -threads syntax/value");
188 }
189 break;
190
191 case CLO_ORDER:
192 if (s_arg[i_arg].n_items != 2 ||
193 sscanf(s_arg[i_arg].list[1], "%ld", &order) != 1 ||
194 order < 1) {
195 SDDS_Bomb("invalid -order syntax/value");
196 }
197 break;
198
199 case CLO_PIPE:
200 if (!processPipeOption(s_arg[i_arg].list + 1, s_arg[i_arg].n_items - 1, &pipeFlags)) {
201 SDDS_Bomb("invalid -pipe syntax");
202 }
203 break;
204
205 case CLO_ABOVERANGE:
206 s_arg[i_arg].n_items -= 1;
207 if (s_arg[i_arg].n_items < 1 ||
208 !scanItemList(&aboveRange.flags, s_arg[i_arg].list + 1, &s_arg[i_arg].n_items, 0,
209 "value", SDDS_DOUBLE, &aboveRange.value, 1, OUTRANGE_VALUE,
210 "skip", -1, NULL, 0, OUTRANGE_SKIP,
211 "saturate", -1, NULL, 0, OUTRANGE_SATURATE,
212 "extrapolate", -1, NULL, 0, OUTRANGE_EXTRAPOLATE,
213 "wrap", -1, NULL, 0, OUTRANGE_WRAP,
214 "abort", -1, NULL, 0, OUTRANGE_ABORT,
215 "warn", -1, NULL, 0, OUTRANGE_WARN, NULL)) {
216 SDDS_Bomb("invalid -aboveRange syntax/value");
217 }
218 if ((i = bitsSet(aboveRange.flags & (OUTRANGE_VALUE | OUTRANGE_SKIP | OUTRANGE_SATURATE |
219 OUTRANGE_EXTRAPOLATE | OUTRANGE_WRAP | OUTRANGE_ABORT))) > 1) {
220 SDDS_Bomb("incompatible keywords given for -aboveRange");
221 }
222 if (i != 1)
223 aboveRange.flags |= OUTRANGE_SATURATE;
224 break;
225
226 case CLO_VERBOSE:
227 //verbose = 1;
228 break;
229
230 case CLO_BELOWRANGE:
231 s_arg[i_arg].n_items -= 1;
232 if (s_arg[i_arg].n_items < 1 ||
233 !scanItemList(&belowRange.flags, s_arg[i_arg].list + 1, &s_arg[i_arg].n_items, 0,
234 "value", SDDS_DOUBLE, &belowRange.value, 1, OUTRANGE_VALUE,
235 "skip", -1, NULL, 0, OUTRANGE_SKIP,
236 "saturate", -1, NULL, 0, OUTRANGE_SATURATE,
237 "extrapolate", -1, NULL, 0, OUTRANGE_EXTRAPOLATE,
238 "wrap", -1, NULL, 0, OUTRANGE_WRAP,
239 "abort", -1, NULL, 0, OUTRANGE_ABORT,
240 "warn", -1, NULL, 0, OUTRANGE_WARN, NULL)) {
241 SDDS_Bomb("invalid -belowRange syntax/value");
242 }
243 if ((i = bitsSet(belowRange.flags & (OUTRANGE_VALUE | OUTRANGE_SKIP | OUTRANGE_SATURATE |
244 OUTRANGE_EXTRAPOLATE | OUTRANGE_WRAP | OUTRANGE_ABORT))) > 1) {
245 SDDS_Bomb("incompatible keywords given for -belowRange");
246 }
247 if (i != 1)
248 belowRange.flags |= OUTRANGE_SATURATE;
249 break;
250
251 case CLO_DATA:
252 s_arg[i_arg].n_items -= 1;
253 if (s_arg[i_arg].n_items < 4) {
254 SDDS_Bomb("invalid -data syntax");
255 }
256 data_control = SDDS_Realloc(data_control, sizeof(*data_control) * (dataControls + 1));
257 data_control[dataControls].fileColumn = data_control[dataControls].interpCol =
258 data_control[dataControls].funcOfCol = data_control[dataControls].atCol = NULL;
259 data_control[dataControls].file = NULL;
260 data_control[dataControls].files = 0;
261 data_control[dataControls].hasdata = 0;
262 data_control[dataControls].colValue = NULL;
263 data_control[dataControls].flags = 0;
264
265 if (!scanItemList(&data_control[dataControls].flags, s_arg[i_arg].list + 1,
266 &s_arg[i_arg].n_items, 0,
267 "fileColumn", SDDS_STRING, &(data_control[dataControls].fileColumn), 1, 0,
268 "interpolate", SDDS_STRING, &(data_control[dataControls].interpCol), 1, 0,
269 "functionof", SDDS_STRING, &(data_control[dataControls].funcOfCol), 1, 0,
270 "column", SDDS_STRING, &(data_control[dataControls].atCol), 1, AT_COLUMN,
271 "atValue", SDDS_DOUBLE, &(data_control[dataControls].atValue), 1, AT_VALUE, NULL) ||
272 !data_control[dataControls].fileColumn ||
273 !data_control[dataControls].interpCol ||
274 !data_control[dataControls].funcOfCol) {
275 SDDS_Bomb("Invalid -data syntax");
276 }
277
278 if (!(data_control[dataControls].flags & AT_COLUMN) &&
279 !(data_control[dataControls].flags & AT_VALUE)) {
280 SDDS_Bomb("Invalid -data syntax: either column or atValue option should be given.");
281 }
282
283 if ((data_control[dataControls].flags & AT_COLUMN) &&
284 (data_control[dataControls].flags & AT_VALUE)) {
285 SDDS_Bomb("Invalid -data syntax: column and atValue options are not compatible.");
286 }
287
288 valid_option = 1;
289 if (dataControls) {
290 if (match_string(data_control[dataControls].funcOfCol, funcOf, dataControls, EXACT_MATCH) > 0) {
291 fprintf(stderr, "Multiple independent columns provided!\n");
292 exit(EXIT_FAILURE);
293 }
294 if (match_string(data_control[dataControls].interpCol, interpCol, dataControls, EXACT_MATCH) > 0) {
295 fprintf(stderr, "Warning: Interpolate column '%s' has been used.\n", data_control[dataControls].interpCol);
296 valid_option = 0;
297 }
298 }
299
300 if (valid_option) {
301 interpCol = SDDS_Realloc(interpCol, sizeof(*interpCol) * (dataControls + 1));
302 funcOf = SDDS_Realloc(funcOf, sizeof(*funcOf) * (dataControls + 1));
303 interpCol[dataControls] = data_control[dataControls].interpCol;
304 funcOf[dataControls] = data_control[dataControls].funcOfCol;
305 dataControls++;
306 }
307 break;
308
309 default:
310 fprintf(stderr, "Error: Unknown or ambiguous option '%s'\n", s_arg[i_arg].list[0]);
311 exit(EXIT_FAILURE);
312 break;
313 }
314 } else {
315 if (!input)
316 input = s_arg[i_arg].list[0];
317 else if (!output)
318 output = s_arg[i_arg].list[0];
319 else
320 SDDS_Bomb("Too many filenames provided.");
321 }
322 }
323
324 processFilenames("sddsinterpset", &input, &output, pipeFlags, 0, NULL);
325
326 if (!SDDS_InitializeInput(&SDDSin, input))
327 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
328
329 for (i = 0; i < dataControls; i++) {
330 if ((index = SDDS_GetColumnIndex(&SDDSin, data_control[i].fileColumn)) < 0) {
331 fprintf(stderr, "Warning: Column '%s' does not exist in input file '%s'.\n",
332 data_control[i].fileColumn, input);
333 continue;
334 }
335 if (SDDS_GetColumnType(&SDDSin, index) != SDDS_STRING) {
336 fprintf(stderr, "Error: Column '%s' in input file '%s' is not a string column.\n",
337 data_control[i].fileColumn, input);
338 continue;
339 }
340 if (data_control[i].atCol) {
341 if ((index = SDDS_GetColumnIndex(&SDDSin, data_control[i].atCol)) < 0) {
342 fprintf(stderr, "Warning: Column '%s' does not exist in input file '%s'.\n",
343 data_control[i].atCol, input);
344 continue;
345 }
346 if (!SDDS_NUMERIC_TYPE(SDDS_GetColumnType(&SDDSin, index))) {
347 fprintf(stderr, "Error: Column '%s' in input file '%s' is not a numeric column.\n",
348 data_control[i].atCol, input);
349 continue;
350 }
351 }
352 data_control[i].hasdata = 1;
353 valid_data++;
354 }
355
356 if (!valid_data) {
357 fprintf(stderr, "Error: No valid -data options provided for processing.\n");
358 exit(EXIT_FAILURE);
359 }
360
361 if (!SDDS_InitializeCopy(&SDDSout, &SDDSin, output, "w"))
362 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
363
364 if (columnMajorOrder != -1)
365 SDDSout.layout.data_mode.column_major = columnMajorOrder;
366 else
367 SDDSout.layout.data_mode.column_major = SDDSin.layout.data_mode.column_major;
368
369 while (SDDS_ReadPage(&SDDSin) > 0) {
370 rows = SDDS_Realloc(rows, sizeof(*rows) * (pages + 1));
371 out_depenValue = SDDS_Realloc(out_depenValue, sizeof(*out_depenValue) * (pages + 1));
372 rowFlag = SDDS_Realloc(rowFlag, sizeof(*rowFlag) * (pages + 1));
373
374 if (!(rows[pages] = SDDS_CountRowsOfInterest(&SDDSin))) {
375 fprintf(stderr, "Error: No data found in input file '%s'.\n", input);
376 exit(EXIT_FAILURE);
377 }
378
379 rowFlag[pages] = (int32_t *)malloc(sizeof(**rowFlag) * rows[pages]);
380 out_depenValue[pages] = calloc(dataControls, sizeof(*out_depenValue[pages]));
381 if (!out_depenValue[pages])
382 SDDS_Bomb("memory allocation failure");
383
384 for (i = 0; i < rows[pages]; i++)
385 rowFlag[pages][i] = 1;
386
387 for (i = 0; i < dataControls; i++) {
388 if (data_control[i].hasdata) {
389 unsigned long *interpCodeRow = NULL;
390 char errorMessage[1024];
391 int failed = 0;
392
393 out_depenValue[pages][i] = malloc(sizeof(*out_depenValue[pages][i]) * rows[pages]);
394 if (!out_depenValue[pages][i])
395 SDDS_Bomb("memory allocation failure");
396
397 data_control[i].files = rows[pages];
398 if (!(data_control[i].file = (char **)SDDS_GetColumn(&SDDSin, data_control[i].fileColumn))) {
399 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
400 }
401
402 if (data_control[i].atCol) {
403 if (!(data_control[i].colValue = SDDS_GetColumnInDoubles(&SDDSin, data_control[i].atCol))) {
404 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
405 }
406 }
407
408 if (!data_control[i].atCol)
409 atValue = data_control[i].atValue;
410
411 if (!pages) {
412 j = rows[pages] - 1;
413 if (!SDDS_InitializeInput(&SDDSdata, data_control[i].file[j]))
414 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
415
416 switch (SDDS_CheckColumn(&SDDSdata, data_control[i].interpCol, NULL, SDDS_ANY_NUMERIC_TYPE, NULL)) {
417 case SDDS_CHECK_OKAY:
418 if (!SDDS_TransferColumnDefinition(&SDDSout, &SDDSdata, data_control[i].interpCol, data_control[i].interpCol))
419 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
420 break;
421 default:
422 fprintf(stderr, "Error: Column '%s' missing or invalid in file '%s'.\n",
423 data_control[i].interpCol, data_control[i].file[j]);
424 exit(EXIT_FAILURE);
425 break;
426 }
427
428 switch (SDDS_CheckColumn(&SDDSdata, data_control[i].funcOfCol, NULL, SDDS_ANY_NUMERIC_TYPE, NULL)) {
429 case SDDS_CHECK_OKAY:
430 if (!(data_control[i].atCol) &&
431 !SDDS_TransferColumnDefinition(&SDDSout, &SDDSdata, data_control[i].funcOfCol, data_control[i].funcOfCol))
432 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
433 break;
434 default:
435 fprintf(stderr, "Error: Column '%s' missing or invalid in file '%s'.\n",
436 data_control[i].funcOfCol, data_control[i].file[j]);
437 exit(EXIT_FAILURE);
438 break;
439 }
440
441 if (!SDDS_Terminate(&SDDSdata))
442 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
443 }
444
445 interpCodeRow = calloc(rows[pages], sizeof(*interpCodeRow));
446 if (!interpCodeRow)
447 SDDS_Bomb("memory allocation failure");
448 errorMessage[0] = 0;
449
450#pragma omp parallel for if (threads > 1 && rows[pages] > 1) num_threads(threads) schedule(dynamic)
451 for (j = 0; j < rows[pages]; j++) {
452 double localAtValue, localResult;
453 unsigned long localInterpCode;
454 char localError[1024];
455 localAtValue = data_control[i].atCol ? data_control[i].colValue[j] : atValue;
456 localResult = 0;
457 localInterpCode = 0;
458 localError[0] = 0;
459
460 if (!interpolateDataFile(data_control[i].file[j], &data_control[i], localAtValue,
461 &belowRange, &aboveRange, order, &localResult, &localInterpCode,
462 localError, sizeof(localError))) {
463#pragma omp critical
464 {
465 if (!failed) {
466 failed = 1;
467 snprintf(errorMessage, sizeof(errorMessage), "%s", localError);
468 }
469 }
470 } else {
471 out_depenValue[pages][i][j] = localResult;
472 interpCodeRow[j] = localInterpCode;
473 if (localInterpCode & OUTRANGE_SKIP)
474 rowFlag[pages][j] = 0;
475 }
476 }
477
478 if (failed) {
479 fprintf(stderr, "%s\n", errorMessage);
480 exit(EXIT_FAILURE);
481 }
482
483 for (j = 0; j < rows[pages]; j++) {
484 if (interpCodeRow[j] & OUTRANGE_ABORT) {
485 fprintf(stderr, "Error: Value %e out of range for column '%s'.\n",
486 data_control[i].atCol ? data_control[i].colValue[j] : atValue, data_control[i].interpCol);
487 exit(EXIT_FAILURE);
488 }
489 if (interpCodeRow[j] & OUTRANGE_WARN)
490 fprintf(stderr, "Warning: Value %e out of range for column '%s'.\n",
491 data_control[i].atCol ? data_control[i].colValue[j] : atValue, data_control[i].interpCol);
492 }
493 free(interpCodeRow);
494 }
495
496 for (j = 0; j < data_control[i].files; j++)
497 free(data_control[i].file[j]);
498 free(data_control[i].file);
499 data_control[i].file = NULL;
500
501 if (data_control[i].colValue) {
502 free(data_control[i].colValue);
503 data_control[i].colValue = NULL;
504 }
505 }
506
507 if (!pages) {
508 if (!SDDS_WriteLayout(&SDDSout))
509 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
510 }
511
512 if (!SDDS_StartTable(&SDDSout, rows[pages]))
513 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
514
515 if (!SDDS_CopyColumns(&SDDSout, &SDDSin))
516 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
517
518 if (!SDDS_CopyParameters(&SDDSout, &SDDSin))
519 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
520
521 for (i = 0; i < dataControls; i++) {
522 if (data_control[i].hasdata) {
523 if (!SDDS_SetColumnFromDoubles(&SDDSout, SDDS_SET_BY_NAME, out_depenValue[pages][i],
524 rows[pages], data_control[i].interpCol)) {
525 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
526 }
527 if (!(data_control[i].atCol)) {
528 for (row = 0; row < rows[pages]; row++) {
529 if (!SDDS_SetRowValues(&SDDSout, SDDS_SET_BY_NAME | SDDS_PASS_BY_VALUE, row,
530 data_control[i].funcOfCol, data_control[i].atValue, NULL)) {
531 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
532 }
533 }
534 }
535 }
536 }
537
538 if (!SDDS_AssertRowFlags(&SDDSout, SDDS_FLAG_ARRAY, rowFlag[pages], rows[pages]))
539 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
540
541 if (!SDDS_WritePage(&SDDSout))
542 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
543
544 pages++;
545 }
546
547 if (!SDDS_Terminate(&SDDSin))
548 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
549
550 if (!SDDS_Terminate(&SDDSout)) {
551 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
552 exit(EXIT_FAILURE);
553 }
554
555 freedatacontrol(data_control, dataControls);
556
557 if (out_depenValue) {
558 for (i = 0; i < pages; i++) {
559 for (j = 0; j < dataControls; j++)
560 free(out_depenValue[i][j]);
561 free(out_depenValue[i]);
562 free(rowFlag[i]);
563 }
564 free(out_depenValue);
565 free(rowFlag);
566 }
567
568 if (interpCol)
569 free(interpCol);
570 if (funcOf)
571 free(funcOf);
572 if (rows)
573 free(rows);
574
575 free_scanargs(&s_arg, argc);
576 return EXIT_SUCCESS;
577}
int32_t SDDS_CopyColumns(SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
Definition SDDS_copy.c:387
int32_t SDDS_CopyParameters(SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source)
Definition SDDS_copy.c:286
int32_t SDDS_InitializeCopy(SDDS_DATASET *SDDS_target, SDDS_DATASET *SDDS_source, char *filename, char *filemode)
Definition SDDS_copy.c:40
int32_t SDDS_SetRowValues(SDDS_DATASET *SDDS_dataset, int32_t mode, int64_t row,...)
int32_t SDDS_SetColumnFromDoubles(SDDS_DATASET *SDDS_dataset, int32_t mode, double *data, int64_t rows,...)
Sets the values for a single data column using double-precision floating-point numbers.
int32_t SDDS_AssertRowFlags(SDDS_DATASET *SDDS_dataset, uint32_t mode,...)
Sets acceptance flags for rows based on specified criteria.
void * SDDS_GetColumn(SDDS_DATASET *SDDS_dataset, char *column_name)
Retrieves a copy of the data for a specified column, including only rows marked as "of interest".
int32_t SDDS_WritePage(SDDS_DATASET *SDDS_dataset)
Writes the current data table to the output file.
int32_t SDDS_WriteLayout(SDDS_DATASET *SDDS_dataset)
Writes the SDDS layout header to the output file.
int32_t SDDS_TransferColumnDefinition(SDDS_DATASET *target, SDDS_DATASET *source, char *name, char *newName)
Transfers a column definition from a source dataset to a target dataset.
int32_t SDDS_GetColumnIndex(SDDS_DATASET *SDDS_dataset, char *name)
Retrieves the index of a named column in the SDDS dataset.
void SDDS_PrintErrors(FILE *fp, int32_t mode)
Prints recorded error messages to a specified file stream.
Definition SDDS_utils.c:474
void SDDS_RegisterProgramName(const char *name)
Registers the executable program name for use in error messages.
Definition SDDS_utils.c:318
int32_t SDDS_GetColumnType(SDDS_DATASET *SDDS_dataset, int32_t index)
Retrieves the data type of a column in the SDDS dataset by its index.
void SDDS_Bomb(char *message)
Terminates the program after printing an error message and recorded errors.
Definition SDDS_utils.c:380
void * SDDS_Realloc(void *old_ptr, size_t new_size)
Reallocates memory to a new size.
Definition SDDS_utils.c:743
#define SDDS_STRING
Identifier for the string data type.
Definition SDDStypes.h:85
#define SDDS_DOUBLE
Identifier for the double data type.
Definition SDDStypes.h:37
#define SDDS_NUMERIC_TYPE(type)
Checks if the given type identifier corresponds to any numeric type.
Definition SDDStypes.h:138
long bitsSet(unsigned long data)
Counts the number of set bits (1s) in the given data.
Definition binary.c:52
long match_string(char *string, char **option, long n_options, long mode)
Matches a given string against an array of option strings based on specified modes.
int scanargs(SCANNED_ARG **scanned, int argc, char **argv)
Definition scanargs.c:36
long processPipeOption(char **item, long items, unsigned long *flags)
Definition scanargs.c:357
void processFilenames(char *programName, char **input, char **output, unsigned long pipeFlags, long noWarnings, long *tmpOutputUsed)
Definition scanargs.c:391
void free_scanargs(SCANNED_ARG **scanned, int argc)
Definition scanargs.c:588
long scanItemList(unsigned long *flags, char **item, long *items, unsigned long mode,...)
Scans a list of items and assigns values based on provided keywords and types.