Why the behaviour differs when fgets() is used instead gets()

136 views Asked by At

as per gcc warning:

the `gets' function is dangerous and should not be used

I try to use fgets() but it does not wok out in my code as you may see the outputs for both at the end of code below. May someone please tell me what mistake (if any) I am doing?

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

#define size 128

int Table[size];

/****ShiftTable Function Declaration****/
void ShiftTable(char Pattern[]);

/****Horspool Function Declaration****/
int Horspool(char Pattern[],char Text[]);

/****Main Function****/
int main()
   {
    char Text[100],Pattern[100];
    int pos;

    printf("Enter the Text : ");
    gets(Text);                    //Works fine
    //fgets(Text,100,stdin);       //Does not work

    printf("\nEnter the Pattern: ");
    gets(Pattern);                 //Works fine
    //fgets(Pattern,100,stdin);    //Does not Work

    pos=Horspool(Pattern,Text);

    if(pos==-1)
            printf("\nPattern Not Found!\n\n");
    else
        printf("\nPattern Found at %d position.\n\n",pos+1);        

    return 0;
   }

/****Horspool Function Definition****/
int Horspool(char Pattern[],char Text[])
   {
    int m,n,i,k;

    n=strlen(Text);
    m=strlen(Pattern);

    ShiftTable(Pattern);

    i=m-1;

    while(i<n)
         {
        k=0;
        while(k<m && (Text[i-k]==Pattern[m-1-k]))  k++;

        if(k==m)   return i-m+1;

        i+=Table[Text[i]];
         }

    return -1;
    }

/****ShifTable Function Definition****/
void ShiftTable(char Pattern[])
    {
    int i,m;
    m=strlen(Pattern);

    for(i=0;i<size;i++)
        Table[i]=m;

    for(i=0;i<m-1;i++)
        Table[Pattern[i]]=m-1-i;
    }

Output:

When I use gets()

majid@majid-K53SC:~ $ ./a.out

Enter the Text : BANGALORE IS GARDEN CITY

Enter the Pattern: GARDEN

Pattern Found at 14 position.

When I use fgets()

majid@majid-K53SC:~ $ ./a.out

Enter the Text : BANGALORE IS GARDEN CITY

Enter the Pattern: GARDEN

Pattern Not Found!

2

There are 2 answers

7
Spikatrix On BEST ANSWER

fgets consumes the newline character (you press Enter after entering the string) and stores it in Text while gets does not. You'll need to strip the newline character off from Text.

So, after both the calls to gets,

Text = "BANGALORE IS GARDEN CITY"
Pattern = "GARDEN"

and in the case of fgets,

Text = "BANGALORE IS GARDEN CITY\n"
Pattern = "GARDEN\n"
0
Sourav Ghosh On

First, thank you for paying heed to the warning. You're very right to switch to fegts().

Now, to answer your question,

Why the behaviour differs when fgets() is used instead gets()?

That is not a weird behaviour. That is the expected behaviour of fgets().

Unlike gets(), fgets() reads and stores the trailing newline into the supplied input buffer. You need to strip off the newline before you go on for the comparison.

Without that, essentially, your inputs look like:

Text    --> "BANGALORE IS GARDEN CITY\n"
Pattern --> "GARDEN\n"

Now, as we know, a "GARDEN " and "GARDEN\n" are not same, so your comparison fails.

That said, just a suggestion, the recommended signature of main() is int main(void).