Algoritmos y Lenguaje de Programación, Sección 1 Ristras Ristras • Ristras, cadenas ó strings )“Hola a todos” • Secuencia de 0 o más caracteres terminada por un 0 o NULL Mario Medina C. [email protected] )No confundir 0 con ‘0’ )NULL termina ristra pero no forma parte de ella ` No es considerado en el largo de la ristra • Secuencias literales Funciones de ristras Largo de una ristra • Declaradas en <string.h> • Funciones de • Número de caracteres en la ristra )Largo ilimitado ` Largo de la ristra dado por el terminador 0 )Largo limitado ` Largo de la ristra es argumento de la función )Sin contar el 0 size_t strlen(char const *string); )Retorna un valor de tipo size_t ` Definido en <stddef.h> como unsigned integer )Argumento es puntero a ristra constante ` Función no puede cambiar la ristra Operaciones con strlen() if (strlen(x) >= 10) if (strlen(x) – 10 >= 0) • No son iguales! )Resta de unsigned integers da un unsigned integer como resultado )Segunda expresión es siempre positiva! ` Forzar resultado a tener signo if ( (signed) strlen(x) – 10 >= 0) ©Mario Medina C. strcpy() char *strcpy(char *dst, char const *src) • Copia la ristra apuntada por *src a la dirección apuntada por *dst )Retorna puntero a dst )src es puntero constante )dst debe ser un ` vector de caracteres ` puntero a un vector ` puntero a memoria dinámica 1 Algoritmos y Lenguaje de Programación, Sección 1 strcpy() • Cuándo termina la copia? )Al encontrar un byte 0 en la ristra origen strcpy() char mensaje[] = “Hola”; char mensaje2[] = “Chao”; strcpy(mensaje, “Adios”); • Qué pasa si src y dst se traslapan? )Comportamiento indefinido • Qué pasa si dst es menor que src? )strcpy() sobreescribirá datos posteriores a dst strcat() char *strcat(char *dst, char const *src) H o l a \0 C h a o \0 A d i o s \0 h a o \0 strcat() char mensaje[10] = “Hola”; strcat(mensaje, “Chao”); • Concatena la ristra apuntada por *src a continuación de la ristra apuntada por *dst )Retorna puntero a dst )Comportamiento indefinido si src y dst se traslapan )Programador debe asegurarse de reservar suficiente espacio para ambas ristras strcmp() int strcmp(char const *s1, char const *s2) • Compara la ristra apuntada por *s1 con la ristra apuntada por *s2 )Comparación caracter a caracter según código ASCII ` Resultado es 0 si s1 es igual a s2 ` Resultado es < 0 si s1 < s2 ` Resultado es > 0 si s1 > s2 ©Mario Medina C. H o l a \0 H o l a C h a o \0 strncpy() char *strncpy(char const *dst, char const *src, size_t len) • Copia exactamente n caracteres de la ristra apuntada por *s1 a la ristra *s2 )Si strlen(src) < len, dst se llena con caracteres NULL )Si strlen(src) > len, dst recibe len caracteres ` NULL terminador se pierde! 2 Algoritmos y Lenguaje de Programación, Sección 1 strncat() char *strncat(char const *dst, char const *src, size_t len) • Concatena hasta n caracteres de la ristra apuntada por *s1 a la ristra *s2 )Si strlen(src) < len, dst se llena con caracteres NULL )Si strlen(src) > len, dst recibe len caracteres strncmp() int strncmp(char const *s1, char const *s1, size_t len) • Compara hasta n caracteres de la ristra apuntada por *s1 y de la ristra *s2 )Si los primeros len caracteres de ambas cadenas son iguales, función retorna 0 ` NULL terminador se pierde! strchr() char *strchr(char const *s, int c) • Revisa la ristra s de izquierda a derecha buscando el caracter c )Retorna un puntero a la primera ocurrencia del caracter )Retorna NULL si el caracter no está presente char *strrchr(char const *s, int c) )Lo mismo, pero revisa de derecha a izquierda strstr() char *strstr(char const *s1, char const *s2) • Revisa la ristra s1 de izquierda a derecha buscando la ristra s2 )Retorna un puntero al comienzo de s2 en s1 )Si s2 no aparece en s1, retorna NULL )Si s2 está vacío, retorna s1 ©Mario Medina C. strpbrk() char *strpbrk(char const *s, char const *grp) • Revisa la ristra s de izquierda a derecha buscando un caracter del grupo grp char s[20] = “Hola a todos”; char *p; p = strpbrk(s, “aeiou”); )Retorna un puntero a la primera ‘o’ strspn(), strcspn() size_t strspn(char const *s, char const *grp) • Cuenta cuántos caracteres de la ristra grp existen al comienzo de la ristra s len = strspn(buffer, “ \n\r\t\f\v”); )len cuenta cuántos caracteres blancos existen al comienzo de buffer )strcspn() es el complemento de strspn() 3 Algoritmos y Lenguaje de Programación, Sección 1 strtok() char *strtok(char *str, char const *sep) • Busca tokens en la ristra str separados por caracteres de sep )Retorna un puntero al elemento encontrado )Si se repite llamada con *str igual a NULL, sigue buscando en ristra original )Modifica la ristra original *str strtok() printTokens(“(56)-(41)-234985”); ) Línea = “(56)-(41)-234985” ` 1er. token = “56” ) Línea = “)-(41)-234985” ` 2do. token = “41” ) Línea = “)-234985” ` 3er. token = “234985” ) Línea = “” ` 4to. token = NULL ) Iteración termina Conversión de ristras • Funciones para una base dada long int strtol(char const *s, char **resto, int base) unsigned long int strtoul(char const *s, char **resto, int base) )resto es puntero al próximo caracter a convertir ` resto puede ser NULL )Base puede estar entre 2 y 36 strtok() printTokens(char *linea){ char sep[] = “(-)”; char *token; for (token = strtok(linea, sep); token != NULL; token = strtok(NULL, sep)) { printf(“Token = %s\n”, token); } } Conversión de ristras • Declaraciones en <stdlib.h> • Funciones convierten ristras de caracteres en valores numéricos enteros • Funciones para base 10 int atoi(char const *s); long int atol(char const *s); )Ignora sufijos no numéricos )atoi(123abc) entrega 123 Conversión de ristras • Funciones convierten ristras de caracteres en valores numéricos de punto flotante )Declaraciones en <math.h> double atof(char const *s); double strtod(char const *s, char **resto); )resto es puntero al próximo caracter a convertir ` resto puede ser NULL ` Dígitos 0-9, A-Z ©Mario Medina C. 4 Algoritmos y Lenguaje de Programación, Sección 1 Clasificación de caracteres • Declaraciones en <ctype.h> • Funciones reciben un entero conteniendo un caracter • Funciones retornan un valor entero para verdadero o falso int iscntrl(int c) Clasificación de caracteres )iscntrl(): Verdadero si argumento es caracter de control )isspace(): Verdadero si argumento es caracter blanco (‘ ‘, ‘\f’, ‘\n’, ‘\t’, ‘\v’) )isdigit(): Verdadero si argumento es dígito entre 0 y 9 )isxdigit(): Verdadero si argumento es dígito entre 0 y 9, a y f, o A y F Clasificación de caracteres Clasificación de caracteres Transformación de caracteres Operaciones con memoria )islower(): Verdadero si argumento es caracter entre a y z )isupper(): Verdadero si argumento es caracter entre A y Z )isalpha(): Verdadero si argumento es caracter entre a y z, o A y Z )isalnum(): Verdadero si argumento es caracter entre a y z, o A y Z, o 0 y 9 )int tolower(int c): retorna su argumento como minúsculas )int toupper(int c): retorna su argumento como mayúsculas )Si argumento no es transformable, se retorna sin cambios )ispunct(): Verdadero si argumento es caracter de puntuación )isgraph(): Verdadero si argumento es caracter gráfico )isprint(): Verdadero si argumento es caracter imprimible (alfanumérico, puntuación, gráfico, espacio) • Ristras terminan en byte de valor 0 • Cómo operar con áreas de memoria que pueden contener un 0? )Usar funciones de manejo de memoria • Similares a funciones strnxxx() )No terminan al encontrar un NULL ©Mario Medina C. 5 Algoritmos y Lenguaje de Programación, Sección 1 memcpy() char *memcpy(void *dst, void const *src, size_t length) • Copia length bytes del área apuntada por *src al área apuntada por *dst )Qué pasa si áreas se traslapan? ` Comportamiento indefinido int area1[numDatos], area2[numDatos]; memcpy(area2, area1, sizeof(area1)); memcmp() int memcmp(void *a, void const *b, size_t length) • Compara length bytes del área apuntada por *src con bytes del área apuntada por *dst )Comparación se hace como unsigned char )Retorna 0 si secuencias son iguales, negativo si a < b, positivo si a > b memmove() char *memmove(void *dst, void const *src, size_t length) • Copia length bytes del área apuntada por *src al área apuntada por *dst )Qué pasa si áreas se traslapan? ` Comportamiento correcto! )memmove() más lento que memcpy() memchr(), memrchr() void *memchr(void const *s, int c, size_t length) • Revisa length bytes del área apuntada por *s de izquierda a derecha buscando el caracter c )Retorna puntero a la primera ocurrencia del caracter )Retorna NULL si el caracter no está presente • *memrchr() hace lo mismo, pero revisa de derecha a izquierda memset() void *memset(void *s, int c, size_t length) • Inicializa length bytes del área apuntada por *s al caracter c )Retorna un puntero al área inicializada ©Mario Medina C. 6