Estoy trabajando en una tarea y como parte de ella necesito extraer el entero de una cadena.
Intenté usar la atoi()
función, pero siempre devuelve a 0
, así que cambié a strtol()
, pero aún devuelve a 0
.
El objetivo es extraer los enteros de la cadena y pasarlos como argumentos a una función diferente. Estoy usando una función que luego usa estos valores para actualizar algunos datos ( update_stats
).
Tenga en cuenta que soy bastante nuevo en la programación en lenguaje C, pero este fue mi intento:
void get_number (char str[]) {
char *end;
int num;
num = strtol(str, &end, 10);
update_stats(num);
num = strtol(end, &end, 10);
update_stats(num);
}
El propósito de esto es en una cadena "e5 d8"
(por ejemplo) extraería el 5
y el 8
de esa cadena.
El formato de la cadena es siempre el mismo.
¿Cómo puedo hacer esto?
c
string-parsing
Ramux05
fuente
fuente
isdigit
antes de usarstrtol
atoi
ystrtol
espere recibir el puntero al primer carácter de un número: su puntero ya debe estar apuntando a un dígito. Ni "e" ni "d" son dígitos cuando la base es 10. Para encontrar los números en la cadena, debe escribir un código para examinar cada carácter y determinar si es un dígito o no. Una vez que haya encontrado un dígito, puede convertirlo (solo un dígito) o la secuencia de dígitos (varios dígitos) a un número, dependiendo de cuál sea su necesidad."e5 d8"
tostrtol
no es una forma correcta de encontrar el "5" y convertirlo en un número.Respuestas:
strtol
no encuentra un número en una cadena. Convierte el número al comienzo de la cadena . (Omite espacios en blanco, pero nada más).Si necesita encontrar dónde comienza un número, puede usar algo como:
(
man strpbrk
)Si sus números pueden estar firmados, necesitará algo un poco más sofisticado. Una forma es hacer lo anterior y luego hacer una copia de seguridad de un personaje si el personaje anterior es
-
. Pero cuidado con el comienzo de la cadena:Simplemente poner
-
en elstrpbrk
argumento produciría coincidencias falsas en entradas comonon-numeric7
.fuente
Si el formato es siempre así, esto también podría funcionar
Salida
%[^0-9]
coincidirá con cualquier carácter que no sea un dígito. Al agregar lo*
mismo, esto%*[^0-9]
indica que los datos deben leerse de la cadena, pero se ignoran.fuente
sscanf
. Realmente aprecio el esfuerzo. Sin embargo, en ninguna parte se especifica que el formato es la forma en que ha dado por sentado. Intenta agregar un poco más de genérico si puedes. Además, si el usuario está atascado en E / S y conversión de cadena a entero, existe una alta probabilidad de que él / ella sea nuevo. Por lo tanto, sería realmente útil agregar o al menos proporcionar un enlace a la documentación, por ejemplo, en este casosscanf
,. Buena respuesta aunque :)sscanf
es la documentación. Creo que lo que realmente puede mejorar aquí es una pequeña explicación del formato, que puedo agregar aquí.Te sugiero que escribas la lógica por tu cuenta. Lo sé, es como reinventar la rueda , pero en ese caso, tendrás una idea de cómo funciona realmente la biblioteca.
Aquí hay una función que propongo:
No olvides pasar una cuerda con un
\0
al final :)fuente
c
, es posible convertir a bool int etrue
yfalse
a1
y0
respectivamente