Both of your versions are wrong and have undefined behaviour. Undefined
behaviour means that the outcome is undefined, anything can happen: a segfault
for example or the appearance that the program runs without a problem.
First of all, never use gets
again, it's a dangerous function that doesn't
take the size of the buffer into account an can lead to buffer overflows. This
function has also been deprecated in C99, so there no real reason to use it, use
fgets
instead.
gets
expects a pointer to a char
array, where it stores the string. If you
pass a NULL
pointer, gets
does not check and writes through a NULL
pointer, which is undefined behaviour.
If you do
char *str;
gets(str);
here you are only declaring a new pointer, but it is uninitialized, meaning that
it's pointing at a random position in memory. In your case it seems that this
random position was a valid one and hence the program has appearance that
everything worked fine. You have to either initialize your pointer and make it
point somewhere valid
char buffer[1024];
char *str = buffer;
fgets(str, 1024, stdin);
or you have to allocate memory with malloc
& friend
char *str = calloc(1024, 1);
if(str == NULL)
{
fprintf(stderr, "not enough memory\n");
return;
}
fgets(str, 1024, stdin);
The reason why many people say that you should initialize a pointer with NULL
is because it allows to check later if a pointer points to some valid position
in memory. For example an algorithm could check if the pointer points to a valid
location, then it continues, otherwise it allocates memory first and then
continues. It's also a good strategy have to free the memory:
char *ptr = NULL;
if(something_is_true())
{
// do stuff
ptr = malloc(...);
// more stuff
}
free(ptr);
Here if something_is_true()
returns false, the free(ptr)
won't end in an
error, because free(NULL)
is valid.