SDDSlib
Loading...
Searching...
No Matches
sddssinefit.c File Reference

Performs a sinusoidal fit on input data using the model: y(n) = a0 + a1*sin(2*PI*a2*x(n) + a3) or y(n) = a0 + a1*sin(2*PI*a2*x(n) + a3) + a4*x(n) More...

#include "mdb.h"
#include "SDDS.h"
#include "scan.h"

Go to the source code of this file.

Macros

#define GUESS_CONSTANT_GIVEN   0x0001
 
#define GUESS_FACTOR_GIVEN   0x0002
 
#define GUESS_FREQ_GIVEN   0x0004
 
#define GUESS_PHASE_GIVEN   0x0008
 
#define GUESS_SLOPE_GIVEN   0x0010
 

Enumerations

enum  option_type {
  SET_TOLERANCE , SET_VERBOSITY , SET_CLUE , SET_GUESS ,
  SET_COLUMNS , SET_FULLOUTPUT , SET_LIMITS , SET_PIPE ,
  SET_MAJOR_ORDER , SET_LOCK_FREQ , SET_ADD_SLOPE , N_OPTIONS
}
 

Functions

double fitFunction (double *a, long *invalid)
 
double fitFunctionWithSlope (double *a, long *invalid)
 
void report (double res, double *a, long pass, long n_eval, long n_dimen)
 
void setupOutputFile (SDDS_DATASET *OutputTable, int32_t *xIndex, int32_t *yIndex, int32_t *fitIndex, int32_t *residualIndex, char *output, long fullOutput, SDDS_DATASET *InputTable, char *xName, char *yName, short columnMajorOrder, short addSlope)
 
char * makeInverseUnits (char *units)
 
int main (int argc, char **argv)
 

Variables

char * option [N_OPTIONS]
 
static char * USAGE
 
static double * xData
 
static double * yData
 
static int64_t nData
 
static double yMin
 
static double yMax
 
static double xMin
 
static double xMax
 
static double fit [5]
 
long verbosity
 

Detailed Description

Performs a sinusoidal fit on input data using the model: y(n) = a0 + a1*sin(2*PI*a2*x(n) + a3) or y(n) = a0 + a1*sin(2*PI*a2*x(n) + a3) + a4*x(n)

This program reads input data from an SDDS (Self Describing Data Sets) file, performs a sinusoidal fit based on the provided parameters and options, and outputs the fitted data along with residuals to an output SDDS file.

License
This file is distributed under the terms of the Software License Agreement found in the file LICENSE included with this distribution.
Author
M. Borland, C. Saunders, R. Soliday, L. Emery, H. Shang, N. Kuklev

Definition in file sddssinefit.c.

Macro Definition Documentation

◆ GUESS_CONSTANT_GIVEN

#define GUESS_CONSTANT_GIVEN   0x0001

Definition at line 106 of file sddssinefit.c.

◆ GUESS_FACTOR_GIVEN

#define GUESS_FACTOR_GIVEN   0x0002

Definition at line 107 of file sddssinefit.c.

◆ GUESS_FREQ_GIVEN

#define GUESS_FREQ_GIVEN   0x0004

Definition at line 108 of file sddssinefit.c.

◆ GUESS_PHASE_GIVEN

#define GUESS_PHASE_GIVEN   0x0008

Definition at line 109 of file sddssinefit.c.

◆ GUESS_SLOPE_GIVEN

#define GUESS_SLOPE_GIVEN   0x0010

Definition at line 110 of file sddssinefit.c.

Enumeration Type Documentation

◆ option_type

enum option_type

Definition at line 28 of file sddssinefit.c.

28 {
29 SET_TOLERANCE,
30 SET_VERBOSITY,
31 SET_CLUE,
32 SET_GUESS,
33 SET_COLUMNS,
34 SET_FULLOUTPUT,
35 SET_LIMITS,
36 SET_PIPE,
37 SET_MAJOR_ORDER,
38 SET_LOCK_FREQ,
39 SET_ADD_SLOPE,
40 N_OPTIONS
41};

Function Documentation

◆ fitFunction()

double fitFunction ( double * a,
long * invalid )

Definition at line 467 of file sddssinefit.c.

467 {
468 int64_t i;
469 double chi;
470 static double min_chi;
471
472 min_chi = DBL_MAX;
473
474 *invalid = 0;
475 for (i = chi = 0; i < nData; i++)
476 chi += sqr(yData[i] - (a[0] + a[1] * sin(PIx2 * a[2] * xData[i] + a[3])));
477 if (isnan(chi) || isinf(chi))
478 *invalid = 1;
479 if (verbosity > 3)
480 fprintf(stderr, "Trial: a = %e, %e, %e, %e --> chi = %e, invalid = %ld\n", a[0], a[1], a[2], a[3], chi, *invalid);
481 if (min_chi > chi) {
482 min_chi = chi;
483 fit[0] = a[0];
484 fit[1] = a[1];
485 fit[2] = a[2];
486 fit[3] = a[3];
487 if (verbosity > 2)
488 fprintf(stderr, "New best chi = %e: a = %e, %e, %e, %e\n", chi, fit[0], fit[1], fit[2], fit[3]);
489 }
490 return chi;
491}

◆ fitFunctionWithSlope()

double fitFunctionWithSlope ( double * a,
long * invalid )

Definition at line 493 of file sddssinefit.c.

493 {
494 int64_t i;
495 double chi;
496 static double min_chi;
497
498 min_chi = DBL_MAX;
499
500 *invalid = 0;
501 for (i = chi = 0; i < nData; i++)
502 chi += sqr(yData[i] - (a[0] + a[1] * sin(PIx2 * a[2] * xData[i] + a[3]) + a[4] * xData[i]));
503 if (isnan(chi) || isinf(chi))
504 *invalid = 1;
505 if (verbosity > 3)
506 fprintf(stderr, "Trial: a = %e, %e, %e, %e, %e --> chi = %e, invalid = %ld\n",
507 a[0], a[1], a[2], a[3], a[4], chi, *invalid);
508 if (min_chi > chi) {
509 min_chi = chi;
510 fit[0] = a[0];
511 fit[1] = a[1];
512 fit[2] = a[2];
513 fit[3] = a[3];
514 fit[4] = a[4];
515 if (verbosity > 2)
516 fprintf(stderr, "New best chi = %e: a = %e, %e, %e, %e, %e\n",
517 chi, fit[0], fit[1], fit[2], fit[3], fit[4]);
518 }
519 return chi;
520}

◆ main()

int main ( int argc,
char ** argv )

Definition at line 112 of file sddssinefit.c.

112 {
113 double tolerance, result;
114 int32_t nEvalMax = 5000, nPassMax = 25;
115 double a[5], da[5];
116 double alo[5], ahi[5];
117 long n_dimen = 4;
118 int64_t zeroes;
119 SDDS_DATASET InputTable, OutputTable;
120 SCANNED_ARG *s_arg;
121 long i_arg, fullOutput;
122 int64_t i;
123 char *input, *output, *xName, *yName;
124 int32_t xIndex, yIndex, fitIndex, residualIndex;
125 long retval;
126 double *fitData, *residualData, rmsResidual;
127 unsigned long guessFlags, dummyFlags, pipeFlags;
128 double constantGuess, factorGuess, freqGuess, phaseGuess, slopeGuess;
129 double firstZero, lastZero;
130 unsigned long simplexFlags = 0, majorOrderFlag;
131 short columnMajorOrder = -1;
132 short lockFreq = 0;
133 short addSlope = 0;
134
136 argc = scanargs(&s_arg, argc, argv);
137 if (argc < 2 || argc > (2 + N_OPTIONS))
138 bomb(NULL, USAGE);
139
140 input = output = NULL;
141 tolerance = 1e-6;
142 verbosity = fullOutput = 0;
143 xName = yName = NULL;
144 guessFlags = 0;
145 pipeFlags = 0;
146
147 for (i_arg = 1; i_arg < argc; i_arg++) {
148 if (s_arg[i_arg].arg_type == OPTION) {
149 switch (match_string(s_arg[i_arg].list[0], option, N_OPTIONS, 0)) {
150 case SET_MAJOR_ORDER:
151 majorOrderFlag = 0;
152 s_arg[i_arg].n_items--;
153 if (s_arg[i_arg].n_items > 0 &&
154 (!scanItemList(&majorOrderFlag, s_arg[i_arg].list + 1, &s_arg[i_arg].n_items, 0,
155 "row", -1, NULL, 0, SDDS_ROW_MAJOR_ORDER,
156 "column", -1, NULL, 0, SDDS_COLUMN_MAJOR_ORDER, NULL)))
157 SDDS_Bomb("invalid -majorOrder syntax/values");
158 if (majorOrderFlag & SDDS_COLUMN_MAJOR_ORDER)
159 columnMajorOrder = 1;
160 else if (majorOrderFlag & SDDS_ROW_MAJOR_ORDER)
161 columnMajorOrder = 0;
162 break;
163 case SET_TOLERANCE:
164 if (s_arg[i_arg].n_items != 2 || sscanf(s_arg[i_arg].list[1], "%lf", &tolerance) != 1)
165 SDDS_Bomb("incorrect -tolerance syntax");
166 break;
167 case SET_VERBOSITY:
168 if (s_arg[i_arg].n_items != 2 || sscanf(s_arg[i_arg].list[1], "%ld", &verbosity) != 1)
169 SDDS_Bomb("incorrect -verbosity syntax");
170 break;
171 case SET_GUESS:
172 if (s_arg[i_arg].n_items < 2)
173 SDDS_Bomb("incorrect -guess syntax");
174 s_arg[i_arg].n_items -= 1;
175 if (!scanItemList(&guessFlags, s_arg[i_arg].list + 1, &s_arg[i_arg].n_items, 0,
176 "constant", SDDS_DOUBLE, &constantGuess, 1, GUESS_CONSTANT_GIVEN,
177 "factor", SDDS_DOUBLE, &factorGuess, 1, GUESS_FACTOR_GIVEN,
178 "frequency", SDDS_DOUBLE, &freqGuess, 1, GUESS_FREQ_GIVEN,
179 "phase", SDDS_DOUBLE, &phaseGuess, 1, GUESS_PHASE_GIVEN,
180 "slope", SDDS_DOUBLE, &slopeGuess, 1, GUESS_SLOPE_GIVEN, NULL))
181 SDDS_Bomb("invalid -guess syntax");
182 break;
183 case SET_COLUMNS:
184 if (s_arg[i_arg].n_items != 3)
185 SDDS_Bomb("invalid -columns syntax");
186 xName = s_arg[i_arg].list[1];
187 yName = s_arg[i_arg].list[2];
188 break;
189 case SET_FULLOUTPUT:
190 fullOutput = 1;
191 break;
192 case SET_LOCK_FREQ:
193 lockFreq = 1;
194 break;
195 case SET_ADD_SLOPE:
196 addSlope = 1;
197 n_dimen = 5;
198 break;
199 case SET_LIMITS:
200 if (s_arg[i_arg].n_items < 2)
201 SDDS_Bomb("incorrect -limits syntax");
202 s_arg[i_arg].n_items -= 1;
203 if (!scanItemList(&dummyFlags, s_arg[i_arg].list + 1, &s_arg[i_arg].n_items, 0,
204 "evaluations", SDDS_LONG, &nEvalMax, 1, 0,
205 "passes", SDDS_LONG, &nPassMax, 1, 0, NULL) ||
206 nEvalMax <= 0 || nPassMax <= 0)
207 SDDS_Bomb("invalid -limits syntax");
208 break;
209 case SET_PIPE:
210 if (!processPipeOption(s_arg[i_arg].list + 1, s_arg[i_arg].n_items - 1, &pipeFlags))
211 SDDS_Bomb("invalid -pipe syntax");
212 break;
213 default:
214 fprintf(stderr, "Error: Unknown or ambiguous option: %s\n", s_arg[i_arg].list[0]);
215 exit(EXIT_FAILURE);
216 break;
217 }
218 } else {
219 if (input == NULL)
220 input = s_arg[i_arg].list[0];
221 else if (output == NULL)
222 output = s_arg[i_arg].list[0];
223 else
224 SDDS_Bomb("Too many filenames provided.");
225 }
226 }
227
228 processFilenames("sddssinefit", &input, &output, pipeFlags, 0, NULL);
229
230 if (!xName || !yName)
231 SDDS_Bomb("-columns option must be specified.");
232
233 if (!SDDS_InitializeInput(&InputTable, input) ||
234 SDDS_GetColumnIndex(&InputTable, xName) < 0 ||
235 SDDS_GetColumnIndex(&InputTable, yName) < 0)
236 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
237
238 setupOutputFile(&OutputTable, &xIndex, &yIndex, &fitIndex, &residualIndex, output, fullOutput,
239 &InputTable, xName, yName, columnMajorOrder, addSlope);
240
241 fitData = residualData = NULL;
242
243 alo[0] = -(ahi[0] = DBL_MAX);
244 alo[1] = alo[2] = 0;
245 ahi[1] = ahi[2] = DBL_MAX;
246 alo[3] = -(ahi[3] = PIx2);
247 if (addSlope) {
248 alo[4] = -(ahi[4] = DBL_MAX);
249 }
250 firstZero = lastZero = 0;
251 while ((retval = SDDS_ReadPage(&InputTable)) > 0) {
252 if (!(xData = SDDS_GetColumnInDoubles(&InputTable, xName)) ||
253 !(yData = SDDS_GetColumnInDoubles(&InputTable, yName)))
254 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
255 if ((nData = SDDS_CountRowsOfInterest(&InputTable)) < 4)
256 continue;
257
258 find_min_max(&yMin, &yMax, yData, nData);
259 find_min_max(&xMin, &xMax, xData, nData);
260 zeroes = 0;
261 for (i = 1; i < nData; i++)
262 if (yData[i] * yData[i - 1] <= 0) {
263 i++;
264 if (!zeroes)
265 firstZero = (xData[i] + xData[i - 1]) / 2;
266 else
267 lastZero = (xData[i] + xData[i - 1]) / 2;
268 zeroes++;
269 }
270 a[0] = (yMin + yMax) / 2;
271 a[1] = (yMax - yMin) / 2;
272 if (!zeroes)
273 a[2] = 2 / fabs(xMax - xMin);
274 else
275 a[2] = zeroes / (2 * fabs(lastZero - firstZero));
276 a[3] = 0;
277 if (addSlope) {
278 a[4] = 0;
279 }
280 if (guessFlags & GUESS_CONSTANT_GIVEN)
281 a[0] = constantGuess;
282 if (guessFlags & GUESS_FACTOR_GIVEN)
283 a[1] = factorGuess;
284 if (guessFlags & GUESS_FREQ_GIVEN)
285 a[2] = freqGuess;
286 if (guessFlags & GUESS_PHASE_GIVEN)
287 a[3] = phaseGuess;
288 if (guessFlags & GUESS_SLOPE_GIVEN)
289 a[4] = slopeGuess;
290
291 alo[1] = a[1] / 2;
292 if (!(da[0] = a[0] * 0.1))
293 da[0] = 0.01;
294 if (!(da[1] = a[1] * 0.1))
295 da[1] = 0.01;
296 da[2] = a[2] * 0.25;
297 da[3] = 0.01;
298 if (addSlope) {
299 da[4] = 0.01;
300 }
301
302 if (lockFreq) {
303 alo[2] = ahi[2] = a[2];
304 da[2] = 0;
305 }
306
307 if (addSlope) {
308 simplexMin(&result, a, da, alo, ahi, NULL, n_dimen, -DBL_MAX, tolerance, fitFunctionWithSlope,
309 (verbosity > 0 ? report : NULL), nEvalMax, nPassMax, 12, 3, 1.0, simplexFlags);
310 } else {
311 simplexMin(&result, a, da, alo, ahi, NULL, n_dimen, -DBL_MAX, tolerance, fitFunction,
312 (verbosity > 0 ? report : NULL), nEvalMax, nPassMax, 12, 3, 1.0, simplexFlags);
313 }
314 fitData = trealloc(fitData, sizeof(*fitData) * nData);
315 residualData = trealloc(residualData, sizeof(*residualData) * nData);
316 if (addSlope) {
317 for (i = result = 0; i < nData; i++) {
318 fitData[i] = a[0] + a[1] * sin(PIx2 * a[2] * xData[i] + a[3]) + a[4] * xData[i];
319 residualData[i] = yData[i] - fitData[i];
320 result += sqr(residualData[i]);
321 }
322 } else {
323 for (i = result = 0; i < nData; i++) {
324 fitData[i] = a[0] + a[1] * sin(PIx2 * a[2] * xData[i] + a[3]);
325 residualData[i] = yData[i] - fitData[i];
326 result += sqr(residualData[i]);
327 }
328 }
329 rmsResidual = sqrt(result / nData);
330 if (verbosity > 1) {
331 fprintf(stderr, "RMS deviation: %.15e\n", rmsResidual);
332 fprintf(stderr, "(RMS deviation)/(largest value): %.15e\n", rmsResidual / MAX(fabs(yMin), fabs(yMax)));
333 }
334 if (verbosity > 0) {
335 if (addSlope) {
336 fprintf(stderr, "Coefficients of fit to the form y = a0 + a1*sin(2*PI*a2*x + a3) + a4*x, a = \n");
337 for (i = 0; i < 5; i++)
338 fprintf(stderr, "%.8e ", a[i]);
339 } else {
340 fprintf(stderr, "Coefficients of fit to the form y = a0 + a1*sin(2*PI*a2*x + a3), a = \n");
341 for (i = 0; i < 4; i++)
342 fprintf(stderr, "%.8e ", a[i]);
343 }
344 fprintf(stderr, "\n");
345 }
346
347 if (!SDDS_StartPage(&OutputTable, nData) ||
348 !SDDS_SetColumn(&OutputTable, SDDS_SET_BY_INDEX, xData, nData, xIndex) ||
349 !SDDS_SetColumn(&OutputTable, SDDS_SET_BY_INDEX, fitData, nData, fitIndex) ||
350 !SDDS_SetParameters(&OutputTable, SDDS_PASS_BY_VALUE | SDDS_SET_BY_NAME,
351 "sinefitConstant", a[0],
352 "sinefitFactor", a[1],
353 "sinefitFrequency", a[2],
354 "sinefitPhase", a[3],
355 "sinefitRmsResidual", rmsResidual,
356 NULL) ||
357 (addSlope &&
358 (!SDDS_SetParameters(&OutputTable, SDDS_PASS_BY_VALUE | SDDS_SET_BY_NAME,
359 "sinefitSlope", a[4], NULL))) ||
360 (fullOutput && (!SDDS_SetColumn(&OutputTable, SDDS_SET_BY_INDEX, yData, nData, yIndex) ||
361 !SDDS_SetColumn(&OutputTable, SDDS_SET_BY_INDEX, residualData, nData, residualIndex))) ||
362 !SDDS_WritePage(&OutputTable))
363 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
364 }
365
366 if (SDDS_Terminate(&InputTable) != 1) {
367 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
368 return EXIT_FAILURE;
369 }
370 if (SDDS_Terminate(&OutputTable) != 1) {
371 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
372 return EXIT_FAILURE;
373 }
374
375 return EXIT_SUCCESS;
376}
int32_t SDDS_StartPage(SDDS_DATASET *SDDS_dataset, int64_t expected_n_rows)
int32_t SDDS_SetParameters(SDDS_DATASET *SDDS_dataset, int32_t mode,...)
int32_t SDDS_SetColumn(SDDS_DATASET *SDDS_dataset, int32_t mode, void *data, int64_t rows,...)
Sets the values for one data column in the current data table of an SDDS dataset.
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:49
int32_t SDDS_Terminate(SDDS_DATASET *SDDS_dataset)
int32_t SDDS_ReadPage(SDDS_DATASET *SDDS_dataset)
int32_t SDDS_WritePage(SDDS_DATASET *SDDS_dataset)
Writes the current data table to the output file.
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:432
void SDDS_RegisterProgramName(const char *name)
Registers the executable program name for use in error messages.
Definition SDDS_utils.c:288
void SDDS_Bomb(char *message)
Terminates the program after printing an error message and recorded errors.
Definition SDDS_utils.c:342
#define SDDS_LONG
Identifier for the signed 32-bit integer data type.
Definition SDDStypes.h:61
#define SDDS_DOUBLE
Identifier for the double data type.
Definition SDDStypes.h:37
void * trealloc(void *old_ptr, uint64_t size_of_block)
Reallocates a memory block to a new size.
Definition array.c:181
void bomb(char *error, char *usage)
Reports error messages to the terminal and aborts the program.
Definition bomb.c:26
int find_min_max(double *min, double *max, double *list, int64_t n)
Finds the minimum and maximum values in a list of doubles.
Definition findMinMax.c:33
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:356
void processFilenames(char *programName, char **input, char **output, unsigned long pipeFlags, long noWarnings, long *tmpOutputUsed)
Definition scanargs.c:390
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.
long simplexMin(double *yReturn, double *xGuess, double *dxGuess, double *xLowerLimit, double *xUpperLimit, short *disable, long dimensions, double target, double tolerance, double(*func)(double *x, long *invalid), void(*report)(double ymin, double *xmin, long pass, long evals, long dims), long maxEvaluations, long maxPasses, long maxDivisions, double divisorFactor, double passRangeFactor, unsigned long flags)
Top-level convenience function for simplex-based minimization.
Definition simplex.c:472

◆ makeInverseUnits()

char * makeInverseUnits ( char * units)

Definition at line 445 of file sddssinefit.c.

445 {
446 char *inverseUnits;
447
448 if (!units || SDDS_StringIsBlank(units))
449 return NULL;
450 inverseUnits = tmalloc(sizeof(*inverseUnits) * (strlen(units) + 5));
451
452 if (strncmp(units, "1/(", 3) == 0 && units[strlen(units) - 1] == ')') {
453 /* Special case of "1/(<unit>)" */
454 strcpy(inverseUnits, units + 3);
455 inverseUnits[strlen(inverseUnits) - 1] = '\0';
456 } else if (!strchr(units, ' ')) {
457 /* Special case of units string without spaces */
458 sprintf(inverseUnits, "1/%s", units);
459 } else {
460 /* General case */
461 sprintf(inverseUnits, "1/(%s)", units);
462 }
463
464 return inverseUnits;
465}
int32_t SDDS_StringIsBlank(char *s)
Checks if a string is blank (contains only whitespace characters).
void * tmalloc(uint64_t size_of_block)
Allocates a memory block of the specified size with zero initialization.
Definition array.c:59

◆ report()

void report ( double res,
double * a,
long pass,
long n_eval,
long n_dimen )

Definition at line 522 of file sddssinefit.c.

522 {
523 long i;
524
525 fprintf(stderr, "Pass %ld, after %ld evaluations: result = %.16e\n", pass, nEval, y);
526 fprintf(stderr, "a = ");
527 for (i = 0; i < n_dimen; i++)
528 fprintf(stderr, "%.8e ", x[i]);
529 fputc('\n', stderr);
530}

◆ setupOutputFile()

void setupOutputFile ( SDDS_DATASET * OutputTable,
int32_t * xIndex,
int32_t * yIndex,
int32_t * fitIndex,
int32_t * residualIndex,
char * output,
long fullOutput,
SDDS_DATASET * InputTable,
char * xName,
char * yName,
short columnMajorOrder,
short addSlope )

Definition at line 378 of file sddssinefit.c.

380 {
381 char *name, *yUnits, *description, *xUnits, *inverse_xUnits;
382 int32_t typeValue = SDDS_DOUBLE;
383 static char *residualNamePart = "Residual";
384 static char *residualDescriptionPart = "Residual of sinusoidal fit to ";
385
386 if (!SDDS_InitializeOutput(OutputTable, SDDS_BINARY, 0, NULL, "sddssinefit output", output) ||
387 !SDDS_TransferColumnDefinition(OutputTable, InputTable, xName, NULL) ||
388 !SDDS_ChangeColumnInformation(OutputTable, "type", &typeValue, SDDS_BY_NAME, xName) ||
389 (*xIndex = SDDS_GetColumnIndex(OutputTable, xName)) < 0 ||
390 !SDDS_GetColumnInformation(InputTable, "units", &xUnits, SDDS_BY_NAME, xName) ||
391 !SDDS_GetColumnInformation(InputTable, "units", &yUnits, SDDS_BY_NAME, yName)) {
392 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors);
393 exit(EXIT_FAILURE);
394 }
395 if (columnMajorOrder != -1)
396 OutputTable->layout.data_mode.column_major = columnMajorOrder;
397 else
398 OutputTable->layout.data_mode.column_major = InputTable->layout.data_mode.column_major;
399
400 name = tmalloc(sizeof(*name) * (strlen(yName) + strlen(residualNamePart) + 1));
401 description = tmalloc(sizeof(*description) * (strlen(yName) + strlen(residualDescriptionPart) + 1));
402
403 if (fullOutput) {
404 if (!SDDS_TransferColumnDefinition(OutputTable, InputTable, yName, NULL) ||
405 !SDDS_ChangeColumnInformation(OutputTable, "type", &typeValue, SDDS_BY_NAME, yName) ||
406 (*yIndex = SDDS_GetColumnIndex(OutputTable, yName)) < 0)
407 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
408 sprintf(name, "%s%s", yName, residualNamePart);
409 sprintf(description, "%s%s", yName, residualDescriptionPart);
410 if ((*residualIndex = SDDS_DefineColumn(OutputTable, name, NULL, yUnits, description, NULL, SDDS_DOUBLE, 0)) < 0)
411 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
412 }
413
414 sprintf(name, "%sFit", yName);
415 sprintf(description, "Sinusoidal fit to %s", yName);
416 if ((*fitIndex = SDDS_DefineColumn(OutputTable, name, NULL, yUnits, description, NULL, SDDS_DOUBLE, 0)) < 0)
417 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
418
419 inverse_xUnits = makeInverseUnits(xUnits);
420
421 if (SDDS_DefineParameter(OutputTable, "sinefitConstant", NULL, yUnits, "Constant term from sinusoidal fit",
422 NULL, SDDS_DOUBLE, 0) < 0 ||
423 SDDS_DefineParameter(OutputTable, "sinefitFactor", NULL, yUnits, "Factor from sinusoidal fit",
424 NULL, SDDS_DOUBLE, 0) < 0 ||
425 SDDS_DefineParameter(OutputTable, "sinefitFrequency", NULL, inverse_xUnits, "Frequency from sinusoidal fit",
426 NULL, SDDS_DOUBLE, 0) < 0 ||
427 SDDS_DefineParameter(OutputTable, "sinefitPhase", NULL, xUnits, "Phase from sinusoidal fit",
428 NULL, SDDS_DOUBLE, 0) < 0 ||
429 SDDS_DefineParameter(OutputTable, "sinefitRmsResidual", NULL, yUnits, "RMS residual from sinusoidal fit",
430 NULL, SDDS_DOUBLE, 0) < 0)
431 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
432
433 if (addSlope) {
434 if (SDDS_DefineParameter(OutputTable, "sinefitSlope", NULL, yUnits, "Slope term added to sinusoidal fit",
435 NULL, SDDS_DOUBLE, 0) < 0)
436 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
437 }
438 if (!SDDS_WriteLayout(OutputTable))
439 SDDS_PrintErrors(stderr, SDDS_VERBOSE_PrintErrors | SDDS_EXIT_PrintErrors);
440
441 free(name);
442 free(description);
443}
int32_t SDDS_ChangeColumnInformation(SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
Modifies a specific field in a column definition within the SDDS dataset.
Definition SDDS_info.c:364
int32_t SDDS_GetColumnInformation(SDDS_DATASET *SDDS_dataset, char *field_name, void *memory, int32_t mode,...)
Retrieves information about a specified column in the SDDS dataset.
Definition SDDS_info.c:41
int32_t SDDS_InitializeOutput(SDDS_DATASET *SDDS_dataset, int32_t data_mode, int32_t lines_per_row, const char *description, const char *contents, const char *filename)
Initializes the SDDS output dataset.
int32_t SDDS_DefineColumn(SDDS_DATASET *SDDS_dataset, const char *name, const char *symbol, const char *units, const char *description, const char *format_string, int32_t type, int32_t field_length)
Defines a data column within the SDDS dataset.
int32_t SDDS_WriteLayout(SDDS_DATASET *SDDS_dataset)
Writes the SDDS layout header to the output file.
int32_t SDDS_DefineParameter(SDDS_DATASET *SDDS_dataset, const char *name, const char *symbol, const char *units, const char *description, const char *format_string, int32_t type, char *fixed_value)
Defines a data parameter with a fixed string value.
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.

Variable Documentation

◆ fit

double fit[5]
static

Definition at line 94 of file sddssinefit.c.

◆ nData

int64_t nData
static

Definition at line 92 of file sddssinefit.c.

◆ option

char* option[N_OPTIONS]
Initial value:
= {
"tolerance",
"verbosity",
"clue",
"guess",
"columns",
"fulloutput",
"limits",
"pipe",
"majorOrder",
"lockFrequency",
"addSlope",
}

Definition at line 43 of file sddssinefit.c.

43 {
44 "tolerance",
45 "verbosity",
46 "clue",
47 "guess",
48 "columns",
49 "fulloutput",
50 "limits",
51 "pipe",
52 "majorOrder",
53 "lockFrequency",
54 "addSlope",
55};

◆ USAGE

char* USAGE
static

Definition at line 57 of file sddssinefit.c.

◆ verbosity

long verbosity

Definition at line 104 of file sddssinefit.c.

◆ xData

double* xData
static

Definition at line 91 of file sddssinefit.c.

◆ xMax

double xMax
static

Definition at line 93 of file sddssinefit.c.

◆ xMin

double xMin
static

Definition at line 93 of file sddssinefit.c.

◆ yData

double * yData
static

Definition at line 91 of file sddssinefit.c.

◆ yMax

double yMax
static

Definition at line 93 of file sddssinefit.c.

◆ yMin

double yMin
static

Definition at line 93 of file sddssinefit.c.