284 {
286 long stats;
288 long requests;
289 SCANNED_ARG *scanned;
291 long i_arg, code, power, iStat, pages, nowarnings = 0;
292 int64_t i, rows, firstRows;
293 char *input, *output;
294 double *inputData, *otherData, indepData, *weight;
295 unsigned long pipeFlags, majorOrderFlag;
296 double decilePoint[2] = {10.0, 90.0};
297 double percentilePoint;
298 double percentile;
299 short columnMajorOrder = -1;
300 int threads = 1;
301
303 argc =
scanargs(&scanned, argc, argv);
304 if (argc < 2) {
305 bomb(
"too few arguments", USAGE);
306 exit(EXIT_FAILURE);
307 }
308 weight = NULL;
309 input = output = NULL;
310 stat = NULL;
311 request = NULL;
312 stats = requests = pipeFlags = 0;
313 rows = firstRows = i = 0;
314
315 for (i_arg = 1; i_arg < argc; i_arg++) {
316 if (scanned[i_arg].arg_type == OPTION) {
317
318 switch (code =
match_string(scanned[i_arg].list[0], option, N_OPTIONS, 0)) {
319 case SET_COPY:
320 case SET_MINIMA:
321 case SET_MAXIMA:
322 case SET_LARGEST:
323 case SET_SIGNEDLARGEST:
324 case SET_MEANS:
325 case SET_SDS:
326 case SET_SIGMAS:
327 case SET_RMSS:
328 case SET_MEDIAN:
329 case SET_DRANGE:
330 case SET_EXMM_MEAN:
331 if (scanned[i_arg].n_items < 2) {
332 fprintf(stderr, "error: invalid -%s syntax\n", option[code]);
333 exit(EXIT_FAILURE);
334 }
335 requests = addStatRequests(&request, requests, scanned[i_arg].list + 1, scanned[i_arg].n_items - 1, code, 0, 0, NULL, 0, NULL);
336 break;
337 case SET_WMEANS:
338 case SET_WSDS:
339 case SET_WRMSS:
340 case SET_WSIGMAS:
341 if (scanned[i_arg].n_items < 3) {
342 fprintf(stderr, "error: invalid -%s syntax\n", option[code]);
343 exit(EXIT_FAILURE);
344 }
345
346 requests = addStatRequests(&request, requests, scanned[i_arg].list + 1, scanned[i_arg].n_items - 1, code, 0, 0, NULL, 1, NULL);
347 break;
348 case SET_SUMS:
349 if (scanned[i_arg].n_items < 3) {
350 fprintf(stderr, "error: invalid -%s syntax\n", option[code]);
351 exit(EXIT_FAILURE);
352 }
353 if (sscanf(scanned[i_arg].list[1], "%ld", &power) != 1 || power < 1) {
354 fprintf(stderr, "error: invalid -%s syntax--bad power in field %s\n", option[code], scanned[i_arg].list[2]);
355 exit(EXIT_FAILURE);
356 }
357 requests = addStatRequests(&request, requests, scanned[i_arg].list + 2, scanned[i_arg].n_items - 2, code, 0, power, NULL, 0, NULL);
358 break;
359 case SET_PERCENTILE:
360 if (scanned[i_arg].n_items < 3) {
361 fprintf(stderr, "error: invalid -%s syntax\n", option[code]);
362 exit(EXIT_FAILURE);
363 }
364 if (sscanf(scanned[i_arg].list[1], "%lf", &percentile) != 1 || percentile < 0 || percentile > 100) {
365 fprintf(stderr, "error: invalid -%s syntax--bad percentage in field %s\n", option[code], scanned[i_arg].list[1]);
366 exit(EXIT_FAILURE);
367 }
368 requests = addStatRequests(&request, requests, scanned[i_arg].list + 2, scanned[i_arg].n_items - 2, code, percentile, 0, NULL, 0, scanned[i_arg].list[1]);
369 break;
370 case SET_SLOPE:
371 case SET_INTERCEPT:
372 case SET_PMINIMA:
373 case SET_PMAXIMA:
374 case SET_CMINIMA:
375 case SET_CMAXIMA:
376 if (scanned[i_arg].n_items < 3) {
377 fprintf(stderr, "error: invalid -%s syntax\n", option[code]);
378 exit(EXIT_FAILURE);
379 }
380 requests = addStatRequests(&request, requests, scanned[i_arg].list + 2, scanned[i_arg].n_items - 2, code, 0, 0, scanned[i_arg].list[1], 0, NULL);
381 break;
382 case SET_PIPE:
383 if (!
processPipeOption(scanned[i_arg].list + 1, scanned[i_arg].n_items - 1, &pipeFlags))
385 break;
386 case SET_NOWARNINGS:
387 nowarnings = 1;
388 break;
389 case SET_MAJOR_ORDER:
390 majorOrderFlag = 0;
391 scanned[i_arg].n_items--;
392 if (scanned[i_arg].n_items > 0 && (!
scanItemList(&majorOrderFlag, scanned[i_arg].list + 1, &scanned[i_arg].n_items, 0,
"row", -1, NULL, 0, SDDS_ROW_MAJOR_ORDER,
"column", -1, NULL, 0, SDDS_COLUMN_MAJOR_ORDER, NULL)))
393 SDDS_Bomb(
"invalid -majorOrder syntax/values");
394 if (majorOrderFlag & SDDS_COLUMN_MAJOR_ORDER)
395 columnMajorOrder = 1;
396 else if (majorOrderFlag & SDDS_ROW_MAJOR_ORDER)
397 columnMajorOrder = 0;
398 break;
399 case SET_THREADS:
400 if (scanned[i_arg].n_items != 2 ||
401 sscanf(scanned[i_arg].list[1], "%d", &threads) != 1 ||
402 threads < 1)
404 break;
405 default:
406 fprintf(stderr, "error: unknown option '%s' given\n", scanned[i_arg].list[0]);
407 exit(EXIT_FAILURE);
408 break;
409 }
410 } else {
411
412 if (!input)
413 input = scanned[i_arg].list[0];
414 else if (!output)
415 output = scanned[i_arg].list[0];
416 else
418 }
419 }
420
422
423 if (!requests)
425
428
429 pages = 0;
431 pages++;
433 SDDS_Bomb(
"empty data page in input file");
434 if (code == 1) {
435 firstRows = rows;
436 if (!(stat = compileStatDefinitions(&inTable, &stats, request, requests))) {
438 exit(EXIT_FAILURE);
439 }
440 if (!setupOutputFile(&outTable, output, &inTable, stat, stats, rows, columnMajorOrder)) {
443 else
444 fprintf(stderr, "Error setting up output file.\n");
445 exit(EXIT_FAILURE);
446 }
447 } else if (firstRows != rows)
448 SDDS_Bomb(
"inconsistent number of rows in input file");
449 for (iStat = 0; iStat < stats; iStat++) {
450 if (stat[iStat].optionCode == SET_COPY) {
451 if (code == 1 && !(stat[iStat].copy =
SDDS_GetColumn(&inTable, stat[iStat].sourceColumn)))
453 continue;
454 }
455 stat[iStat].copy = NULL;
458 switch (stat[iStat].optionCode) {
459 case SET_MINIMA:
460 if (code == 1)
461#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
462 for (i = 0; i < rows; i++)
463 stat[iStat].value1[i] = inputData[i];
464 else
465#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
466 for (i = 0; i < rows; i++)
467 if (stat[iStat].value1[i] > inputData[i])
468 stat[iStat].value1[i] = inputData[i];
469 break;
470 case SET_MAXIMA:
471 if (code == 1)
472#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
473 for (i = 0; i < rows; i++)
474 stat[iStat].value1[i] = inputData[i];
475 else
476#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
477 for (i = 0; i < rows; i++)
478 if (stat[iStat].value1[i] < inputData[i])
479 stat[iStat].value1[i] = inputData[i];
480 break;
481 case SET_CMINIMA:
482
485 if (code == 1)
486#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
487 for (i = 0; i < rows; i++) {
488 stat[iStat].value2[i] = inputData[i];
489 stat[iStat].value1[i] = otherData[i];
490 }
491 else
492#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
493 for (i = 0; i < rows; i++)
494 if (stat[iStat].value2[i] > inputData[i]) {
495 stat[iStat].value2[i] = inputData[i];
496 stat[iStat].value1[i] = otherData[i];
497 }
498 free(otherData);
499 break;
500 case SET_CMAXIMA:
501
504 if (code == 1)
505#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
506 for (i = 0; i < rows; i++) {
507 stat[iStat].value2[i] = inputData[i];
508 stat[iStat].value1[i] = otherData[i];
509 }
510 else
511#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
512 for (i = 0; i < rows; i++)
513 if (stat[iStat].value2[i] < inputData[i]) {
514 stat[iStat].value2[i] = inputData[i];
515 stat[iStat].value1[i] = otherData[i];
516 }
517 free(otherData);
518 break;
519 case SET_LARGEST:
520 if (code == 1)
521#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
522 for (i = 0; i < rows; i++)
523 stat[iStat].value1[i] = fabs(inputData[i]);
524 else
525#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
526 for (i = 0; i < rows; i++)
527 if (stat[iStat].value1[i] < fabs(inputData[i]))
528 stat[iStat].value1[i] = fabs(inputData[i]);
529 break;
530 case SET_SIGNEDLARGEST:
531 if (code == 1)
532#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
533 for (i = 0; i < rows; i++)
534 stat[iStat].value1[i] = inputData[i];
535 else
536#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
537 for (i = 0; i < rows; i++)
538 if (fabs(stat[iStat].value1[i]) < fabs(inputData[i]))
539 stat[iStat].value1[i] = inputData[i];
540 break;
541 case SET_MEANS:
542 if (code == 1)
543#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
544 for (i = 0; i < rows; i++)
545 stat[iStat].value1[i] = inputData[i];
546 else
547#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
548 for (i = 0; i < rows; i++)
549 stat[iStat].value1[i] += inputData[i];
550 break;
551 case SET_WMEANS:
554#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
555 for (i = 0; i < rows; i++) {
556 stat[iStat].sumWeight[i] += weight[i];
557 stat[iStat].value1[i] += inputData[i] * weight[i];
558 }
559 free(weight);
560 break;
561 case SET_SDS:
562 case SET_SIGMAS:
563 if (code == 1)
564#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
565 for (i = 0; i < rows; i++) {
566 stat[iStat].value1[i] = inputData[i];
567 stat[iStat].value2[i] = inputData[i] * inputData[i];
568 }
569 else
570#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
571 for (i = 0; i < rows; i++) {
572 stat[iStat].value1[i] += inputData[i];
573 stat[iStat].value2[i] += inputData[i] * inputData[i];
574 }
575 break;
576 case SET_WSDS:
577 case SET_WSIGMAS:
580#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
581 for (i = 0; i < rows; i++) {
582 stat[iStat].sumWeight[i] += weight[i];
583 stat[iStat].value1[i] += inputData[i] * weight[i];
584 stat[iStat].value2[i] += inputData[i] * inputData[i] * weight[i];
585 }
586 free(weight);
587 break;
588 case SET_RMSS:
589 if (code == 1)
590#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
591 for (i = 0; i < rows; i++)
592 stat[iStat].value1[i] = inputData[i] * inputData[i];
593 else
594#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
595 for (i = 0; i < rows; i++)
596 stat[iStat].value1[i] += inputData[i] * inputData[i];
597 break;
598 case SET_WRMSS:
601#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
602 for (i = 0; i < rows; i++) {
603 stat[iStat].sumWeight[i] += weight[i];
604 stat[iStat].value1[i] += inputData[i] * inputData[i] * weight[i];
605 }
606 free(weight);
607 break;
608 case SET_SUMS:
609 if (code == 1)
610#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
611 for (i = 0; i < rows; i++)
612 stat[iStat].value1[i] =
ipow(inputData[i], stat[iStat].sumPower);
613 else
614#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
615 for (i = 0; i < rows; i++)
616 stat[iStat].value1[i] +=
ipow(inputData[i], stat[iStat].sumPower);
617 break;
618 case SET_PMINIMA:
620 fprintf(stderr, "error: unable to get value of parameter %s\n", stat[iStat].functionOf);
622 }
623 if (code == 1)
624#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
625 for (i = 0; i < rows; i++) {
626 stat[iStat].value2[i] = inputData[i];
627 stat[iStat].value1[i] = indepData;
628 }
629 else
630#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
631 for (i = 0; i < rows; i++) {
632 if (stat[iStat].value2[i] > inputData[i]) {
633 stat[iStat].value2[i] = inputData[i];
634 stat[iStat].value1[i] = indepData;
635 }
636 }
637 break;
638 case SET_PMAXIMA:
640 fprintf(stderr, "error: unable to get value of parameter %s\n", stat[iStat].functionOf);
642 }
643 if (code == 1)
644#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
645 for (i = 0; i < rows; i++) {
646 stat[iStat].value2[i] = inputData[i];
647 stat[iStat].value1[i] = indepData;
648 }
649 else
650#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
651 for (i = 0; i < rows; i++) {
652 if (stat[iStat].value2[i] < inputData[i]) {
653 stat[iStat].value2[i] = inputData[i];
654 stat[iStat].value1[i] = indepData;
655 }
656 }
657 break;
658 case SET_SLOPE:
659 case SET_INTERCEPT:
661 fprintf(stderr, "error: unable to get value of parameter %s\n", stat[iStat].functionOf);
663 }
664
665
666
667
668
669
670 if (code == 1)
671#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
672 for (i = 0; i < rows; i++) {
673 stat[iStat].value1[i] = indepData;
674 stat[iStat].value2[i] = indepData * indepData;
675 stat[iStat].value3[i] = inputData[i];
676 stat[iStat].value4[i] = indepData * inputData[i];
677 }
678 else
679#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
680 for (i = 0; i < rows; i++) {
681 stat[iStat].value1[i] += indepData;
682 stat[iStat].value2[i] += indepData * indepData;
683 stat[iStat].value3[i] += inputData[i];
684 stat[iStat].value4[i] += indepData * inputData[i];
685 }
686 break;
687 case SET_MEDIAN:
688 case SET_DRANGE:
689 case SET_PERCENTILE:
690 case SET_EXMM_MEAN:
691 if (code == 1)
692#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
693 for (i = 0; i < rows; i++) {
694 stat[iStat].array[i] =
tmalloc(
sizeof(*stat[iStat].array[i]));
695 stat[iStat].array[i][pages - 1] = inputData[i];
696 }
697 else {
698#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
699 for (i = 0; i < rows; i++) {
700 stat[iStat].array[i] =
SDDS_Realloc(stat[iStat].array[i],
sizeof(*stat[iStat].array[i]) * pages);
701 stat[iStat].array[i][pages - 1] = inputData[i];
702 }
703 }
704 break;
705 default:
706 SDDS_Bomb(
"invalid statistic code (accumulation loop)");
707 break;
708 }
709 free(inputData);
710 }
711 }
712 if (pages == 0)
714 for (iStat = 0; iStat < stats; iStat++) {
715 switch (stat[iStat].optionCode) {
716 case SET_COPY:
717 case SET_MINIMA:
718 case SET_MAXIMA:
719 case SET_PMINIMA:
720 case SET_PMAXIMA:
721 case SET_CMINIMA:
722 case SET_CMAXIMA:
723 case SET_LARGEST:
724 case SET_SIGNEDLARGEST:
725 case SET_SUMS:
726 break;
727 case SET_MEANS:
728#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
729 for (i = 0; i < rows; i++)
730 stat[iStat].value1[i] /= pages;
731 break;
732 case SET_WMEANS:
733 for (i = 0; i < rows; i++)
734 if (stat[iStat].sumWeight[i])
735 stat[iStat].value1[i] /= stat[iStat].sumWeight[i];
736 else {
737 if (!nowarnings)
738 fprintf(stderr, "warning: the total weight for the %" PRId64 "th row of %s is zero.\n", i + 1, stat[iStat].sourceColumn);
739 stat[iStat].value1[i] = DBL_MAX;
740 }
741 break;
742 case SET_SDS:
743 if (pages < 2) {
744#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
745 for (i = 0; i < rows; i++)
746 stat[iStat].value1[i] = DBL_MAX;
747 } else {
748#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
749 for (i = 0; i < rows; i++) {
750 double tmp1;
751 if ((tmp1 = stat[iStat].value2[i] / pages - sqr(stat[iStat].value1[i] / pages)) <= 0)
752 stat[iStat].value1[i] = 0;
753 else
754 stat[iStat].value1[i] = sqrt(tmp1 * pages / (pages - 1.0));
755 }
756 }
757 break;
758 case SET_WSDS:
759 if (pages < 2) {
760#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
761 for (i = 0; i < rows; i++)
762 stat[iStat].value1[i] = DBL_MAX;
763 } else {
764 for (i = 0; i < rows; i++) {
765 double tmp1;
766 if (stat[iStat].sumWeight[i]) {
767 if ((tmp1 = stat[iStat].value2[i] / stat[iStat].sumWeight[i] - sqr(stat[iStat].value1[i] / stat[iStat].sumWeight[i])) <= 0)
768 stat[iStat].value1[i] = 0;
769 else
770 stat[iStat].value1[i] = sqrt(tmp1 * pages / (pages - 1.0));
771 } else {
772 if (!nowarnings)
773 fprintf(stderr, "Warning, the total weight for the %" PRId64 "th row of %s is zero.\n", i + 1, stat[iStat].sourceColumn);
774 stat[iStat].value1[i] = DBL_MAX;
775 }
776 }
777 }
778 break;
779 case SET_SIGMAS:
780 if (pages < 2) {
781#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
782 for (i = 0; i < rows; i++)
783 stat[iStat].value1[i] = DBL_MAX;
784 } else {
785#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
786 for (i = 0; i < rows; i++) {
787 double tmp1;
788 if ((tmp1 = stat[iStat].value2[i] / pages - sqr(stat[iStat].value1[i] / pages)) <= 0)
789 stat[iStat].value1[i] = 0;
790 else
791 stat[iStat].value1[i] = sqrt(tmp1 / (pages - 1.0));
792 }
793 }
794 break;
795 case SET_WSIGMAS:
796 if (pages < 2) {
797#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
798 for (i = 0; i < rows; i++)
799 stat[iStat].value1[i] = DBL_MAX;
800 } else {
801 for (i = 0; i < rows; i++) {
802 double tmp1;
803 if (stat[iStat].sumWeight[i]) {
804 if ((tmp1 = stat[iStat].value2[i] / stat[iStat].sumWeight[i] - sqr(stat[iStat].value1[i] / stat[iStat].sumWeight[i])) <= 0)
805 stat[iStat].value1[i] = 0;
806 else
807 stat[iStat].value1[i] = sqrt(tmp1 / (pages - 1.0));
808 } else {
809 if (!nowarnings)
810 fprintf(stderr, "Warning, the total weight for the %" PRId64 "th row of %s is zero.\n", i + 1, stat[iStat].sourceColumn);
811 stat[iStat].value1[i] = DBL_MAX;
812 }
813 }
814 }
815 break;
816 case SET_RMSS:
817#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
818 for (i = 0; i < rows; i++)
819 stat[iStat].value1[i] = sqrt(stat[iStat].value1[i] / pages);
820 break;
821 case SET_WRMSS:
822 for (i = 0; i < rows; i++) {
823 if (stat[iStat].sumWeight[i])
824 stat[iStat].value1[i] = sqrt(stat[iStat].value1[i] / stat[iStat].sumWeight[i]);
825 else {
826 if (!nowarnings)
827 fprintf(stderr, "Warning, the total weight for the %" PRId64 "th row of %s is zero.\n", i + 1, stat[iStat].sourceColumn);
828 stat[iStat].value1[i] = DBL_MAX;
829 }
830 }
831 break;
832 case SET_SLOPE:
833#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
834 for (i = 0; i < rows; i++) {
835 double D;
836 D = pages * stat[iStat].value2[i] - stat[iStat].value1[i] * stat[iStat].value1[i];
837 stat[iStat].value1[i] = (pages * stat[iStat].value4[i] - stat[iStat].value1[i] * stat[iStat].value3[i]) / D;
838 }
839 break;
840 case SET_INTERCEPT:
841#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
842 for (i = 0; i < rows; i++) {
843 double D;
844 D = pages * stat[iStat].value2[i] - stat[iStat].value1[i] * stat[iStat].value1[i];
845 stat[iStat].value1[i] = (stat[iStat].value2[i] * stat[iStat].value3[i] - stat[iStat].value1[i] * stat[iStat].value4[i]) / D;
846 }
847 break;
848 case SET_MEDIAN:
849#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
850 for (i = 0; i < rows; i++) {
851 compute_median(&stat[iStat].value1[i], stat[iStat].array[i], pages);
852 }
853 break;
854 case SET_DRANGE:
855#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
856 for (i = 0; i < rows; i++) {
857 double decileResult[2];
859 stat[iStat].value1[i] = 0;
860 else
861 stat[iStat].value1[i] = decileResult[1] - decileResult[0];
862 }
863 break;
864 case SET_PERCENTILE:
865 percentilePoint = stat[iStat].percentile;
866#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
867 for (i = 0; i < rows; i++) {
868 double percentileResult;
869 if (!
compute_percentiles(&percentileResult, &percentilePoint, 1, stat[iStat].array[i], pages))
870 stat[iStat].value1[i] = 0;
871 else
872 stat[iStat].value1[i] = percentileResult;
873 }
874 break;
875 case SET_EXMM_MEAN:
876#pragma omp parallel for if (threads > 1 && rows > 1) num_threads(threads)
877 for (i = 0; i < rows; i++)
878 if (!compute_mean_exclude_min_max(&(stat[iStat].value1[i]), stat[iStat].array[i], pages))
879 stat[iStat].value1[i] = 0;
880 break;
881 default:
882 SDDS_Bomb(
"invalid statistic code (final loop)");
883 break;
884 }
885 if (stat[iStat].optionCode == SET_COPY) {
886 if (!
SDDS_SetColumn(&outTable, SDDS_SET_BY_NAME, stat[iStat].copy, rows, stat[iStat].resultColumn)) {
887 fprintf(stderr, "error setting column values for column %s\n", stat[iStat].resultColumn);
889 }
890 }
else if (!
SDDS_SetColumnFromDoubles(&outTable, SDDS_SET_BY_NAME, stat[iStat].value1, rows, stat[iStat].resultColumn)) {
891 fprintf(stderr, "error setting column values for column %s\n", stat[iStat].resultColumn);
893 }
894 if (stat[iStat].value1)
895 free(stat[iStat].value1);
896 if (stat[iStat].value2)
897 free(stat[iStat].value2);
898 if (stat[iStat].value3)
899 free(stat[iStat].value3);
900 if (stat[iStat].value4)
901 free(stat[iStat].value4);
902 if (stat[iStat].copy)
903 free(stat[iStat].copy);
904 if (stat[iStat].array) {
905 for (i = 0; i < rows; i++) {
906 free(stat[iStat].array[i]);
907 }
908 free(stat[iStat].array);
909 }
910 if (stat[iStat].sumWeight)
911 free(stat[iStat].sumWeight);
912 free(stat[iStat].sourceColumn);
913 free(stat[iStat].resultColumn);
914 stat[iStat].value1 = stat[iStat].value2 = stat[iStat].value3 = stat[iStat].value4 = NULL;
915 stat[iStat].copy = NULL;
916 stat[iStat].array = NULL;
917 }
918 free(stat);
921 return EXIT_SUCCESS;
922}
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_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.
int32_t SDDS_WritePage(SDDS_DATASET *SDDS_dataset)
Writes the current data table to the output file.
void SDDS_RegisterProgramName(const char *name)
Registers the executable program name for use in error messages.
int32_t SDDS_NumberOfErrors()
Retrieves the number of errors recorded by SDDS library routines.
void bomb(char *error, char *usage)
Reports error messages to the terminal and aborts the program.
double ipow(const double x, const int64_t p)
Compute x raised to the power p (x^p).
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)
long processPipeOption(char **item, long items, unsigned long *flags)
void processFilenames(char *programName, char **input, char **output, unsigned long pipeFlags, long noWarnings, long *tmpOutputUsed)
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.