char *s_gets(char * st, int n);
returns a pointer to char
, while
char s_gets(char * st, int n);
returns a plain char
.
I would like to ask also why is there a pointer in the function declaration in the first place? What is its purpose?
It indicates that the function returns a pointer value.
C declaration syntax uses something called a declarator to convey the pointer-ness, array-ness, function-ness, or combination thereof of an item. For example, take the declaration
int *p;
The type of p
is int *
(pointer to int
). The type is specified by the combination of the type specifier int
and the declarator *p
. The int
-ness of p
is given by the type specifier int
and the pointer-ness is given by the declarator *p
.
If you substitute p
with f(void)
, you get
int *f(void);
The type of f
is "function returning pointer to int
". The pointer-ness and function-ness of f
are specified with the declarator *f(void)
.
For any type T
and any declarator D
, the following are true:
T D; // D is an instance of T
T D[N]; // D is an array of T
T D(); // D is a function returning T
T *D; // D is a *pointer* to T
T *D[N]; // D is an array of pointers to T
T *D(); // D is a function returning a pointer to T
T (*D)[N]; // D is a pointer to an array of T
T (*D)(); // D is a pointer to a function returning T
In both declarations and expressions, the postfix []
subscript and ()
function-call operators have higher precedence than unary *
, so *a[N]
will always be parsed as *(a[N])
(array of pointers). To declare something as a pointer to an array or a pointer to a function, you need to explicitly group the *
operator with the declarator using parentheses.
Declarators can get arbitrarily complex:
T (*D())[N]; // D is a function returning a pointer to an array of T
T (*D[N])(); // D is an array of pointers to functions returning T
T *(*(*D)[N])[M]; // D is a pointer to an array of pointers to an array of pointers to T