csv_parse.c en C
Un lector de CSV completo: partir líneas en campos, recortarlos, resumir.
#include <ctype.h>
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#define MAX_FIELDS 8
static char *trim(char *text) {
while (isspace((unsigned char) *text)) {
text++;
}
char *end = text + strlen(text);
while (end > text && isspace((unsigned char) end[-1])) {
end--;
}
*end = '\0';
return text;
}
static int split(char *line, char sep, char **fields, int max) {
int count = 0;
char *start = line;
for (char *p = line;; p++) {
if (*p == sep || *p == '\0') {
int last = (*p == '\0');
*p = '\0';
if (count < max) {
fields[count++] = trim(start);
}
if (last) {
break;
}
start = p + 1;
}
}
return count;
}
static int is_number(const char *text) {
if (*text == '\0') {
return 0;
}
char *end = NULL;
strtod(text, &end);
return *end == '\0';
}
int main(void) {
char rows[3][64] = {
"lang, tpm, accuracy",
"rust, 104, 97.5",
" sql , 88 , 99.0 ",
};
int numeric = 0;
int textual = 0;
for (int r = 0; r < 3; r++) {
char *fields[MAX_FIELDS];
int n = split(rows[r], ',', fields, MAX_FIELDS);
printf("row %d:", r);
for (int i = 0; i < n; i++) {
printf(" [%s]", fields[i]);
if (r > 0) {
if (is_number(fields[i])) {
numeric++;
} else {
textual++;
}
}
}
printf("\n");
}
printf("%-10s %d\n", "numeric", numeric);
printf("%-10s %d\n", "text", textual);
return 0;
}
Cómo funciona
- El parser trabaja sobre una copia mutable para poder cortar en el lugar.
- Cada campo se recorta y se clasifica como numérico o texto.
- Los totales se imprimen como una tabla alineada al final.
Palabras clave y builtins usados aquí
NULLbreakcharconstelseforifintreturnstaticunsignedvoidwhile
El intento, en números
- Líneas
- 80
- Caracteres a escribir
- 1267
- Tokens
- 452
- Ritmo de tres estrellas
- 105 tpm
Al ritmo de tres estrellas de 105 tokens por minuto, este intento toma unos 258 segundos.
Paso 1 de 1 en Bis; paso 13 de 13 en Cadenas y texto.