numtools

perform numerical operations on vectors and matrices in unix pipes
git clone git://src.adamsgaard.dk/numtools # fast
git clone https://src.adamsgaard.dk/numtools.git # slow
Log | Files | Refs | README | LICENSE Back to index

commit b6731286f9cd7efd11eafb989f04acb26edd696e
parent 2e9d87b259dcacf7c74ce8ca85554b05d08533d0
Author: Anders Damsgaard <anders@adamsgaard.dk>
Date:   Mon,  2 May 2022 13:33:30 +0200

add range(1) tool

Diffstat:
MMakefile | 6++++--
Arange.1 | 109+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Arange.c | 69+++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++
Mrangetest.1 | 1+
4 files changed, 183 insertions(+), 2 deletions(-)

diff --git a/Makefile b/Makefile @@ -1,7 +1,7 @@ .POSIX: NAME = mathtools -VERSION = 0.2.5 +VERSION = 0.2.6 # paths PREFIX = /usr/local @@ -12,6 +12,7 @@ BIN =\ max\ mean\ min\ + range\ rangetest\ sum\ transpose\ @@ -54,6 +55,7 @@ ${OBJ}: ${HDR} max: max.o mean: mean.o min: min.o +range: range.o rangetest: rangetest.o sum: sum.o transpose: transpose.o @@ -64,7 +66,7 @@ ${BIN}: ${LIB} ${OBJ} .c.o: ${CC} ${_CFLAGS} ${_CPPFLAGS} -o $@ -c $< -install: +install: # installing executable files and scripts. mkdir -p "${DESTDIR}${PREFIX}/bin" cp -f ${BIN} ${SCRIPTS} "${DESTDIR}${PREFIX}/bin" diff --git a/range.1 b/range.1 @@ -0,0 +1,109 @@ +.Dd $Mdocdate$ +.Dt RANGE 1 +.Os +.Sh NAME +.Nm range +.Nd generates an evenly spaced vector over a spacified range +.Sh SYNOPSIS +.Nm +.Ar cmd +.Op Fl e +.Op Fl f Ar fmtstr +.Op Fl h +.Op Fl l +.Op Fl n Ar num +.Ar min_val +.Ar max_val +.Sh DESCRIPTION +.Nm +generates floating-point numbers that are by default evenly distributed +in the linear, closed interval [ +.Ar min_val +, +.Ar max_val ]. +.Pp +The options are as follows: +.Bl -tag -width Ds +.It Fl b +Do not include +.Ar min_val +as the first value, making it a half-open interval ] +.Ar min_val +, +.Ar max_val ], +or an entirely open interval when combined with +.Ar e . +.It Fl e +Do not include +.Ar max_val +as the last value, making it a half-open interval [ +.Ar min_val +, +.Ar max_val [, +or an entirely open interval when combined with +.Ar b . +.It Fl f Ar fmtstr +Formatting string to use as documented in +.Xr printf 3 . +When including a format specifier (%..), only use forms that are +compatible with +.Vt double +types. +The default format string is '%g'. +.It Fl h +Show usage information. +.It Fl l +Produce output with even intervals in logarithmic space between 10^min_val +and 10^max_val. +.It Fl n Ar num +Number of values to produce within the specified range. +The default is 10. +.El +.Sh EXAMPLES +Generate four equally-spaced numbers in the closed range [0;1]: +.Pp +.Dl $ range -n 4 0 1 +.Dl 0 +.Dl 0.33333 +.Dl 0.66667 +.Dl 1 +.Pp +Same as the previous example, but with full +.Vt double +precision on a 64-bit system: +.Pp +.Dl $ range -n 4 -f '%.17g' 0 1 +.Dl 0 +.Dl 0.33333333333333331 +.Dl 0.66666666666666663 +.Dl 1 +.Pp +Generate four numbers in the range ]0;1[: +.Pp +.Dl $ range -b -e -n 4 0 1 +.Dl 0.2 +.Dl 0.4 +.Dl 0.6 +.Dl 0.8 +.Pp +Repeat and modify a string three times: +.Pp +.Dl $ range -n 3 -f 'The best number is %.0g' 1 3 +.Dl The best number is 1 +.Dl The best number is 2 +.Dl The best number is 3 +.Pp +Generate three numbers evenly distributed in logspace from 10^0 to 10^3: +.Pp +.Dl $ range -l -n 3 0 2 +.Dl 1 +.Dl 10 +.Dl 100 +.Sh SEE ALSO +.Xr max 1 , +.Xr mean 1 , +.Xr min 1 , +.Xr rangetest 1 , +.Xr sum 1 +.Sh AUTHORS +.An Anders Damsgaard Aq Mt anders@adamsgaard.dk diff --git a/range.c b/range.c @@ -0,0 +1,69 @@ +#include <stdio.h> +#include <stdlib.h> +#include <err.h> +#include <limits.h> +#include <string.h> +#include <math.h> + +#include "arg.h" +#include "util.h" + +char *argv0; + +static void +usage(void) +{ + errx(1, "usage: %s [-b] [-e] [-f fmtstr] [-h] [-l] [-n num]" + "min_val max_val\n", argv0); +} + +int +main(int argc, char *argv[]) +{ + int i, ret, n = 10, logrange = 0, openstart = 0, openend = 0; + double minv, maxv, dx; + char fmtstr[PATH_MAX] = "%g"; + + ARGBEGIN { + case 'b': + openstart = 1; + break; + case 'e': + openend = 1; + break; + case 'f': + ret = snprintf(fmtstr, sizeof(fmtstr), "%s", EARGF(usage())); + if (ret < 0 || (size_t)ret >= sizeof(fmtstr)) + errx(1, "%s: could not write fmtstr", __func__); + break; + case 'h': + usage(); + break; + case 'l': + logrange = 1; + break; + case 'n': + n = atoi(EARGF(usage())); + break; + default: + usage(); + } ARGEND; + + if (argc == 2) { + minv = atof(argv[0]); + maxv = atof(argv[1]); + dx = (maxv - minv)/(n - 1 + openend + openstart); + if (minv >= maxv) + errx(1, "min_val must be smaller than max_val"); + for (i = 0 + openstart; i < n + openstart; i++) { + if (logrange) + printf(fmtstr, pow(10, minv + i * dx)); + else + printf(fmtstr, minv + i * dx); + putchar('\n'); + } + } else + usage(); + + return 0; +} diff --git a/rangetest.1 b/rangetest.1 @@ -94,6 +94,7 @@ while surpressing its output: .Xr max 1 , .Xr mean 1 , .Xr min 1 , +.Xr range 1 , .Xr sum 1 .Sh AUTHORS .An Anders Damsgaard Aq Mt anders@adamsgaard.dk