Как выйти из функции scanf, если введено определенное значение?

#c

#c

Вопрос:

Я хочу, чтобы scanf считывал и сохранял некоторые данные в нескольких переменных. Однако, если первая переменная, т. Е. Количество, равно 0, то scanf должен выйти, запрашивая ввод пользователя, поскольку мой следующий цикл while зависит от этого значения, т. Е. Количества. Если значение не равно нулю, продолжайте цикл и выполняйте дальнейшую работу, в противном случае не делайте этого.

 #include <stdio.h>

struct inventory {

    int quantity, category;
    double price, soldByWeight;
    char name[20];
};

void main(void) {

    struct inventory arr[5] = { 0 };

    printf("Enter values: n");

    for (int i = 0; i < 5; i  ) {

        scanf("%d%*c%d%*c%lf%*c%lf%*c[^n]", amp;arr[i].quantity, amp;arr[i].category, amp;arr[i].price, amp;arr[i].soldByWeight, arr[i].name);

        /*while (arr[i].quantity != 0) {

            do some stuff 
        }*/
    }
    return 0;
}
 

Пример ввода 1: 21,1,1.5,1, картофель

Пример ввода 2: 0

Здесь после примерного ввода 2 scanf все еще ожидает ввода от пользователя, если я введу 0 и нажму клавишу ввода. Как я могу выйти из функции scanf после того, как я ввел 0 вместе с клавишей enter. %*c используется для удаления запятых, используемых при вводе примера.

Ответ №1:

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

Затем используйте sscanf для синтаксического анализа строки и всегда проверяйте, что она возвращает.

Наконец, if sscanf возвращает 1 значение, затем проверьте arr[i].quantity , равно ли его значение нулю или нет.

В качестве альтернативы вы также можете выполнить предварительную проверку ввода 0 (перед вызовом sscanf ), используя, например strtol .

Ответ №2:

Вы можете прочитать всю строку, используя fgets . Затем выйдите из цикла for, если строка содержит только 0. В противном случае выполните синтаксический анализ полей с помощью sscanf .

 #include <stdio.h>

struct inventory {

    int quantity, category;
    double price, soldByWeight;
    char name[20];
};

int main() {
    struct inventory arr[5] = { 0 };

    char buf[2048];

    printf("Enter values: n");

    for (int i = 0; i < 5; i  ) {

        fgets(buf, sizeof(buf), stdin);
        if ((buf[0] == '0') amp;amp; ((buf[1] == 'n') || ((buf[1] == 'r') amp;amp; (buf[2] == 'n')))) {
            break;
        }

        sscanf(buf, "%d,%d,%lf,%lf,[^n]", amp;arr[i].quantity, amp;arr[i].category, amp;arr[i].price, amp;arr[i].soldByWeight, arr[i].name);
        printf("%d %d %lf %lf %sn", arr[i].quantity, arr[i].category, arr[i].price, arr[i].soldByWeight, arr[i].name);
    }
    return 0;
}
 

Комментарии:

1. У меня проблема с вашим решением, о которой я забыл упомянуть. Один из входных данных, которые у меня есть, — это строка, разделенная пробелом, однако, когда мы используем %s в sscanf для синтаксического анализа входных данных в массив имен, он отбрасывает все после пробела, поскольку %s имеет ограничение на пробелы. Любая идея о том, как обращаться с пробелами в строке имени символа [20]. Пример ввода: 2,3,9.5,1, итальянская колбаса

2. Пример ввода: 2,3,9.5,1, итальянская колбаса —-> здесь он должен обрабатывать пробел после итальянского

3. Пример ввода: 2,3,9.5,1, итальянская колбаса ——> здесь нужно убрать пробел перед итальянским

4. Хорошо. Я обновил свой ответ выше, чтобы обрабатывать пробел в имени.