Правильный инструмент для этого задания: strtol()
:
- использовать переменные
char *p;
int val, seconds;
- инициализировать его, чтобы он указывал на строку для анализа, инициализировать
seconds
до 0. - в al oop:
- анализировать число с помощью `val = strtol (p, 0, & p);
- пропустить пробелы в
p
: while (*p == ' ') p++;
- если в конце строки вернуть число
seconds
. - проверить для различных возможных единиц, включая формы множественного числа, если вы найдете совпадение:
- умножьте
val
на количество секунд в блоке и добавьте это к seconds
, - , пропустите строку единицы
- , продолжите l oop
- если нет совпадения: пожаловаться на нераспознанную единицу и вернуть -1.
Вот простая реализация:
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
static struct unit {
const char name[8];
int seconds;
} const units[] = {
{ "year", 365 * 24 * 60 * 60 }, { "years", 365 * 24 * 60 * 60 },
{ "month", 30 * 24 * 60 * 60 }, { "months", 30 * 24 * 60 * 60 },
{ "week", 7 * 24 * 60 * 60 }, { "weeks", 7 * 24 * 60 * 60 },
{ "day", 24 * 60 * 60 }, { "days", 24 * 60 * 60 },
{ "hour", 60 * 60 }, { "hours", 60 * 60 },
{ "minute", 60 }, { "minutes", 60 },
{ "second", 1 }, { "seconds", 1 },
};
int parse_time(const char *p) {
int seconds = 0;
while (*p) {
size_t i, n, len;
int val = strtol(p, (char **)&p, 0);
p += strspn(p, " \t\r\n");
if (*p != '\0' && !(*p >= '0' && *p <= '9')) {
len = strcspn(p, " \t\r\n");
for (i = 0, n = sizeof(units) / sizeof(units[0]); i < n; i++) {
if (strlen(units[i].name) == len && !memcmp(p, units[i].name, len))
break;
}
if (i == n) {
printf("unknown unit: %.*s\n", (int)len, p);
return -1;
}
p += len;
val *= units[i].seconds;
}
seconds += val;
}
return seconds;
}
int main(int argc, char *argv[]) {
char buf[256];
if (argc > 1) {
while (*++argv)
printf("%s -> %d seconds\n", *argv, parse_time(*argv));
} else {
for (;;) {
printf("> ");
fflush(stdout);
if (!fgets(buf, sizeof buf, stdin))
break;
printf(" -> %d seconds\n", parse_time(buf));
}
}
return 0;
}