Как проверить строку для диапазона строк в C? - PullRequest
0 голосов
/ 23 декабря 2018

Мне нужно создать Solitaire Program на C. У меня настроена структура данных, но у меня есть вопрос о сравнении строк.

Пользовательский ввод должен выглядеть как «move [color] [value]to [stack] ".

Теперь я планировал использовать strncmp, чтобы увидеть, содержит ли строка " move " " color " и т. д. Но с "значение" У меня есть диапазон из 13 допустимых входных данных (от туза до короля), что означает, что мне потребуется 13 различных операторов if.Есть ли более элегантный способ проверить, какое «значение» содержит вход?

Примеры: «переместить красные 4 на 3» или «переместить черные К на 6»

После того, как я определил, что указал пользователь, я должен найти данную карту в 7 двойных связанных списках ипереместите его в другой список, указанный пользователем.

Спасибо!

1 Ответ

0 голосов
/ 23 декабря 2018

Если ваш ввод для значения представляет собой один символ, вы можете просто проверить, существует ли этот символ в списке допустимых символов:

const char valid_values[] = "A23456789TJQK";
if (strchr(valid_values, input_value[0])) {
    // valid
} else {
    // invalid
}

Вы можете даже использовать сам символ как есть какпредставление значения (поскольку оно уникально и оптимально мало при 1 char).Или вы можете преобразовать в числовое значение, взяв индекс (например, вычитая valid_values из не- NULL возвращаемого значения strchr) и добавив 1.

Если вы хотитеразрешить множественные альтернативы (такие как «A», «ace» или «two», «2», «deuce»), простая альтернатива - создать массив пар строк-значений и перебирать их, пока не будет найдено совпадение иликонец достигнут:

struct value_string {
    const char *string;
    int value;
};
const struct value_string valid_values[] = {
    { .string = "A", .value = 1 },
    { .string = "ace", .value = 1 },
    { .string = "2", .value = 2 },
    { .string = "two", .value = 2 },
    // …
    { .string = "K", .value = 13 },
    { .string = NULL, .value = 0 } // terminator
};

int card_value = 0;
for (const struct value_string *p = valid_values; p->string; ++p) {
    if (strcmp(p->string, input_value) == 0) {
        // found match
        card_value = p->value;
        break;
    }
}
if (card_value) {
    // valid
} else {
    // invalid
}

Преимущества такого рода решения заключаются в ясности и расширяемости кода, а не в улучшении производительности или уменьшении общего количества строк.Для лучшей производительности я бы ожидал, что справочную таблицу (или просто switch) по первому символу, а затем ручную символьную проверку (только из оставшихся возможностей) будет трудно превзойти.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...