Ich habe mich daran gewöhnt strtod
und Varianten. Ich frage mich, warum es keine gibt strtoi
versendet mit <stdlib.h>
. Warum bleibt der Integer-Typ bei dieser Party außen vor?
Insbesondere frage ich, warum es keine Version von gibt atoi
mit den Sicherheitsmerkmalen von strtod
?
strtol()
wandelt einen String in einen Integer um, einen Long Integer aber trotzdem einen Integer. Es gibt atoi()
aber es sollte in den meisten Fällen vermieden werden, da es keinen Mechanismus zur Fehlerberichterstattung bei ungültigen Eingaben gibt.
Warum gibt es kein strtoi in stdlib.h?
Keine kritische Notwendigkeit.
Im frühen C gab es keinen Standard-Integer-Typ mit Vorzeichen, der breiter als war long
und alle engeren Umbauten, wie int
könnte daraus gemacht werden strtol()
– wie unten ausgeführt.
Diese und ihre unsigned
Gegenstücken fehlen jetzt C-Funktionen und ein Designmangel in der aktuellen Standard-C-Bibliothek (C17/18).
Auf vielen Systemen long
und int
haben die gleiche Reichweite und es besteht daher weniger Bedarf an einem separaten strtoi()
. atoi()
erfüllt die Notwendigkeit für Quick-and-Dirty-Code zur Konvertierung in eine int
, kann aber Fehlererkennung vermissen lassen. Bei Fehler, atoi()
entsteht undefiniertes Verhalten (UB). Es gibt auch keine strto_short()
Noch strto_signchar()
etc.
Es ist ziemlich einfach, einen Ersatz zu schaffen strtoi()
. Vereinfachungen bestehen.
#include <errno.h>
#include <limits.h>
#include <stdlib.h>
static long str2subrange(const char *s, char **endptr, int base,
long min, long max) {
long y = strtol(s, endptr, base);
if (y > max) {
errno = ERANGE;
return max;
}
if (y < min) {
errno = ERANGE;
return min;
}
return y;
}
// OP's goal
int str2i(const char *s, char **endptr, int base) {
#if INT_MAX == LONG_MAX && INT_MIN == LONG_MIN
return (int) strtol(s, endptr, base);
#else
return (int) str2subrange(s, endptr, base, INT_MIN, INT_MAX);
#endif
}
short str2short(const char *s, char **endptr, int base) {
return (short) str2subrange(s, endptr, base, SHRT_MIN, SHRT_MAX);
}
signed char str2schar(const char *s, char **endptr, int base) {
return (signed char) str2subrange(s, endptr, base, SCHAR_MIN, SCHAR_MAX);
}
#include <stdint.h>
int16_t str2int16(const char *s, char **endptr, int base) {
return (int16_t) str2subrange(s, endptr, base, INT16_MIN, INT16_MAX);
}
[Edit 2021]
Um Konflikte zu vermeiden Zukünftige BibliotheksrichtungenNamen geändert von strto...()
zu str2...()
.
2
impliziert to
.
Funktionsnamen, die mit beginnen str
, mem
oder wcs
und ein Kleinbuchstabe kann den Deklarationen in hinzugefügt werden <string.h>
Header. C17dr § 7.31.13 1
Die Ganzzahl wird nicht aus der Party ausgelassen: Es gibt sie strtol
das eine Zeichenfolge in a konvertiert long
bei dem es sich um einen ganzzahligen Typ handelt.
Dies ist, was ich verwendet habe.
long long_val;
int int_value;
errno = 0;
long_val = strtol (theString, NULL, 10);
if (errno)
handle_error;
if ((long) someIntMin > long_val || long_val > (long) someIntMax)
handle_invalid;
int_value = (int) long_val;
Es ist Anruf atoi
. Siehe auch Wikipedia für Details, einschließlich seines Nachfolgers strol
.
Übersehen Sie nicht die SEE ALSO
Abschnitt Ihrer Manpages 🙂
SEE ALSO
atof(3), atoi(3), atol(3), strtol(3), strtoul(3)
Du schaust nach atoi(3)
. 🙂