xp10r3r
xp10r3r

Reputation: 33

Getting an infinite running program when using scanf

I'm getting an infinite running programm when I use the following code to read a string from keyboard and save it within a structured vector.

scanf("%s", strk_zgr_fp->bezeichnung, (int)sizeof(strk_zgr_fp->bezeichnung - 1));

Simply nothing happens after this line is reached and the program runs infinitly.

I know scanf() isn't recommended. We're using it only within our C beginners course and I want you to keep it in mind, ie please don't recommend other function rather than above mentioned for the moment.

Any help is much appreciated, thanks in advance.

#include <stdio.h>

typedef struct {
    int nummer;
    char bezeichnung;
    int menge;
    float preis;
} artikel;

void eingabe_artikel(artikel *strk_zgr_fp, int i_fp);
void ausgabe_artikel(artikel *strk_zgr_fp, int i_fp);

void main(void) {
    artikel artikelliste[10];
    artikel *strk_zgr;

    int anzahl;

    do {
        printf("Bitte eine #Artikel eingeben [<= 10]: ");
        scanf("%d", &anzahl);

        if(anzahl < 1 || 10 < anzahl)
            printf("\nEs wurde eine falsche #Artikel eingegeben.");
    } while(anzahl < 1 || 10 < anzahl);

    for(int i = 0; i < anzahl; i++)
        eingabe_artikel(&artikelliste[i], i);

    int i;
    for(strk_zgr = artikelliste, i = 0; strk_zgr < artikelliste + anzahl; 
        strk_zgr++, i++)
        ausgabe_artikel(strk_zgr, i);
}

void eingabe_artikel(artikel *strk_zgr_fp, int i_fp) {
    printf("\nBitte den %d. Artikel eingeben: ", ++i_fp);

    printf("\nNummer: ");
    scanf("%d", &strk_zgr_fp->nummer);

    printf("Bezeichnung: );
    scanf("%s", strk_zgr_fp, (int)sizeof(strk_zgr_fp->bezeichnung - 1));     /* <-- */

    printf("Menge: ");
    scanf("%d", &strk_zgr_fp->menge);

    float preis;
    printf("Preis: );
    scanf("%f", &preis);
    strk_zgr_fp->preis = preis;
}

void ausgabe_artikel(artikel *strk_zgr_fp, int i_fp) {
    printf("\n%d. Artikel: ", ++i_fp);

    printf("\nNummer:\t%d", strk_zgr_fp->nummer);
    printf("\nBezeichnung:\t%s", strk_zgr_fp->bezeichnung);
    printf("\nMenge:\t%d", strk_zgr_fp->menge);
    printf("\nPreis:\t%.2f EUR\n", strk_zgr_fp->preis);    
}

NetBeans Version

Complier Version

Upvotes: 2

Views: 95

Answers (2)

GermanNerd
GermanNerd

Reputation: 653

I tried it out and it worked fine for me. Not sure on this sprintf() function. Could you please explain why I'm supposed to use it? By now, I used this code: char format_str[20]; format_str[0] = '%'; strcat(format_str, "s"); printf("Bezeichnung: "); scanf(format_str, strk_zgr_fp->bezeichnung);

While that works, you are missing out on limiting the length of the user's input. That is why I proposed using sprintf() to create a (sub)string containing the maximal allowable length of the user input, depending on how large your 'bezeichnung' is defined in the struct. Suppose 'bezeichnung' has a limit of 100 characters, you would want to limit the input to 99 (+1 for the zero-termination), so you want a scanf format string like this: "%99s".

chux has provided a much more compact version of my three lines, but I think, in the beginning, you will have it easier to just assemble such format strings piece by piece, at the same time learning how to a) change individual characters in a string, how to use sprintf() in a basic way, and how to concatenate strings with strcat().

There was another example which I did and the course leader provided a scanf() function like this to read a string: scanf("%s", &(strk_zgr_fp->bezeichnung));. I thought when I'm reading a string the address operator isn't used. The only difference is the address operator now is used and the element was put into brackets.

Now, I think this is bad practice. It works, but is superfluous. Consider this small code snippet:

#include <stdio.h>
#include <stdlib.h>

struct test{
    int i;
    char a_str[10];
};

int main()
{
    struct test a_test;
    printf("Normal array adress taking: %p\n", a_test.a_str);
    printf("Using '&' to take adress of array: %p\n", &(a_test.a_str));
    return 0;
}

Hope that helps.

Upvotes: 0

GermanNerd
GermanNerd

Reputation: 653

Many problems in the code. Please at least fix the missing ending quotes on the printf() calls.

Now to the beef:

1) Your structure is wrong. 'Bezeichnung' is defined as a single character, not a string.

typedef struct {
   int nummer;
   char bezeichnung[100];
   int menge;
   float preis;
} artikel;

2) You cannot use scanf() in the way you did. If you want to limit the input length (which always is a good idea), you need to pass the maximum length into the format string. Do you nee to use scanf()?? Because it gets messy from here on.... As your maximum input length might be variable or subject to change (see 1.), you need to build the format string for scanf. Something like this:

char format_str[15];
format_str[0] = '%';
//Dont use itoa(), it is not C standard.
sprintf(&format_str[1], "%d", (int)sizeof(strk_zgr_fp->bezeichnung) - 1);
strcat(format_str, "s");
scanf(format_str, strk_zgr_fp->bezeichnung);     

Hope that gets you going.

PS: You need to include string.h for strcat().

Upvotes: 1

Related Questions