The famous quote for Linux Shell is ‘Where there is a shell, there is a way’. It reflects that the Linux Shell (e.g. BASH) is so powerful that almost every daily jobs can be accomplished by shell commands/utilities. The shell itself is essentially a programming language.
On linux, there is a seq command that will generate the number series between two number ranges and you can specify a incremental step.
And not just integers, seq supports float numbers as well. For example,
The default values for [start] and [incremental step] are 1. And there are two useful options -s to specify the delimiter between generated numbers and -f to specify the outputting format, in the same way as we have for printf, currently %f (for floating), %e (for scientific number notation) and %g (default, the integers).
The space between option and values can be omitted. For example, -s. is the same as -s .
This is useful, for example, if we want to compute the
So, we can use
seq -f '4/%g' 1 2 99999 | paste -sd-+
to generate series like: (the paste will merge these lines using the delimiter minus and plus signs.
4/1-4/3+4/5-4/7+4/9-4/11+4/13-4/15+4/17-4/19 ...
and piped the string into bc -l, the calculator for the computation of
So, the core algorithm can be written into this small beautiful neat function, although it might look complex at first.
1 2 3 4 5 6 7 8 9 10 | void seq(double start, double step, double stop, char *format, char *sep) { char f[MAX_LENGTH]; double i; strcpy(f, format); strcat(f, sep); for (i = start; (i + step >= start) && (i + step <= stop); i += step) { printf(f, i * 1.0); } printf(format, i * 1.0); // there is no delimiter after the last number } |
void seq(double start, double step, double stop, char *format, char *sep) { char f[MAX_LENGTH]; double i; strcpy(f, format); strcat(f, sep); for (i = start; (i + step >= start) && (i + step <= stop); i += step) { printf(f, i * 1.0); } printf(format, i * 1.0); // there is no delimiter after the last number }
And the more complex part of this particular utility should be analysis of the command line options. And we should deal with two options -s and -f for now.
The pre-compiled windows binaries can be downloaded [here, zipped, 3.89kb]
The %e is the scientific representation, that every number can be written as a^e+b, for example.
Now, the full C++ source code is:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 | /* HelloACM.com */ #include <string.h> #include <stdio.h> #include <stdlib.h> const int MAX_LENGTH = 255; void seq(double start, double step, double stop, char *format, char *sep) { char f[MAX_LENGTH]; double i; strcpy(f, format); strcat(f, sep); for (i = start; (i + step >= start) && (i + step <= stop); i += step) { printf(f, i * 1.0); } printf(format, i * 1.0); } int main(int argc, char **argv) { if (argc == 1) { printf("seq: missing operand\n"); printf("Usage: seq [-s separator -f format] start step stop\n"); printf("Usage: seq [-s separator -f format] start stop\n"); printf("Usage: seq [-s separator -f format] stop\n"); printf("by http://HelloACM.com"); return 1; } /* default values */ double first = 1; double inc = 1; double stop = 1; char format[MAX_LENGTH] = "%g"; char sep[MAX_LENGTH] = "\n"; double nums[3]; int j = 0; for (int i = 1; i < argc; i ++) { int curlen = strlen(argv[i]); if ((curlen >= 2) && (argv[i][0] == '-')) { if (argv[i][1] == 'f') { // format if (curlen == 2) { if (i + 1 < argc) { strcpy(format, argv[i + 1]); i ++; continue; } else { printf("Missing format"); return 2; } } else { strncpy(format, argv[i] + 2, curlen - 2); format[curlen - 1] = '\0'; continue; } } else if (argv[i][1] == 's') { // separator if (curlen == 2) { if (i + 1 < argc) { strcpy(sep, argv[i + 1]); i ++; continue; } else { printf("Missing separator"); return 2; } } else { strncpy(sep, argv[i] + 2, curlen - 2); sep[curlen - 1] = '\0'; continue; } } } nums[j ++] = atof(argv[i]); if (j == 3) { if (i + 1 < argc) { printf("Extra operand"); return 3; } } } if (j == 0) { printf("Missing operand"); return 2; } else if (j == 1) { stop = nums[0]; } else if (j == 2) { first = nums[0]; stop = nums[1]; } else { first = nums[0]; inc = nums[1]; stop = nums[2]; } seq(first, inc, stop, (char*)format, (char*)sep); return 0; } |
/* HelloACM.com */ #include <string.h> #include <stdio.h> #include <stdlib.h> const int MAX_LENGTH = 255; void seq(double start, double step, double stop, char *format, char *sep) { char f[MAX_LENGTH]; double i; strcpy(f, format); strcat(f, sep); for (i = start; (i + step >= start) && (i + step <= stop); i += step) { printf(f, i * 1.0); } printf(format, i * 1.0); } int main(int argc, char **argv) { if (argc == 1) { printf("seq: missing operand\n"); printf("Usage: seq [-s separator -f format] start step stop\n"); printf("Usage: seq [-s separator -f format] start stop\n"); printf("Usage: seq [-s separator -f format] stop\n"); printf("by http://HelloACM.com"); return 1; } /* default values */ double first = 1; double inc = 1; double stop = 1; char format[MAX_LENGTH] = "%g"; char sep[MAX_LENGTH] = "\n"; double nums[3]; int j = 0; for (int i = 1; i < argc; i ++) { int curlen = strlen(argv[i]); if ((curlen >= 2) && (argv[i][0] == '-')) { if (argv[i][1] == 'f') { // format if (curlen == 2) { if (i + 1 < argc) { strcpy(format, argv[i + 1]); i ++; continue; } else { printf("Missing format"); return 2; } } else { strncpy(format, argv[i] + 2, curlen - 2); format[curlen - 1] = '\0'; continue; } } else if (argv[i][1] == 's') { // separator if (curlen == 2) { if (i + 1 < argc) { strcpy(sep, argv[i + 1]); i ++; continue; } else { printf("Missing separator"); return 2; } } else { strncpy(sep, argv[i] + 2, curlen - 2); sep[curlen - 1] = '\0'; continue; } } } nums[j ++] = atof(argv[i]); if (j == 3) { if (i + 1 < argc) { printf("Extra operand"); return 3; } } } if (j == 0) { printf("Missing operand"); return 2; } else if (j == 1) { stop = nums[0]; } else if (j == 2) { first = nums[0]; stop = nums[1]; } else { first = nums[0]; inc = nums[1]; stop = nums[2]; } seq(first, inc, stop, (char*)format, (char*)sep); return 0; }
–EOF (The Ultimate Computing & Technology Blog) —
Last Post: Recursive Combination Algorithm Implementation in C++
Next Post: Set Up 8-bit Ultimate Famicom Game Console - BBG (BBK) - with Keyboard and Floppy Drive - USB Floppy Emulator - NES Game Console