Reputation: 11017
I am very much a c newbie and I am learning by following CS107 videos from Standford (I am not a Student there).
Links are below if anyone is interested
Looking at the below implementation of strtok
, I am not sure why the first if statement is written this way: if (s == NULL && ((s = p) == NULL))
char *strtok(char *s, const char *sep)
{
static char *p = NULL;
if (s == NULL && ((s = p) == NULL))
return NULL;
s += strspn(s, sep);
if (!*s)
return p = NULL;
p = s + strcspn(s, sep);
if (*p)
*p++ = '\0';
else
p = NULL;
return s;
}
Here's what I have identified so far:
1) the static
p
is a local static so that it persists once a token is found, and reset to NULL when no more are found2) subsequent calls of
strtoken
pass ins
asNULL
Therefore wouldn't the first check be the same if it were written as:
if (s == NULL && p == NULL)
Or is there a reason it is written the way it is?
Finally: return p = NULL
; is this just a shorthand for:
p = NULL;
return p;
Amazing CS107 Lectures from 2011
Upvotes: 4
Views: 895
Reputation: 13580
if (s == NULL && ((s = p) == NULL))
is not really the same as
if (s == NULL && p == NULL)
although they have the same result, when s
and p
are NULL
.
You've identified correctly that subsequent calls of strtok
must be passed
with NULL
, however if the are still tokens to be returned, p
is not going
to test for NULL
.
So the ((s = p) == NULL)
is a clever trick to assign s
to point to the
rest of the string where more token might be found.
In C when you evaluate an expression like A && B
, A
gets evaluated and B
gets only evaluated if and only if A
was evaluated as true, the reason for
this are sequent points.
If s
is not NULL
, then ((s = p) == NULL)
is never evaluated, s = p
is
never assigned.
If s
is NULL
, then ((s = p) == NULL)
gets evaluated. First s = p
is
evaluated and this is an assignment. If p
is not NULL
, then s
points to
where p
is pointing (the rest of the source) and when compared to NULL
, it
is evaluated to false, thus the return NULL
is not executed and the function
continues looking for tokens.
If however p
is also NULL
, s
is set to point to NULL
and when compared
to NULL
it evaluates to true, the whole if
evaluates to true and return NULL
is executed. When s
initially is NULL
and p
is NULL
, then that
means that all token have been found and return, so the function should return
NULL
. It can be rewritten as:
if(s == NULL)
{
if(p == NULL)
return NULL;
s = p;
}
...
Note that the value of an assignment is the value of the assigment itself.
return a = b;
is the same as doing
a = b;
return b;
Upvotes: 4
Reputation: 2866
Therefore wouldn't the first check be the same if it were written as:
if (s == NULL && p == NULL)
When p
is NULL, yes. When p
is not NULL, no. Because then the side effect of s=p
doesn't happen. And this value s
is used later when the if
statement is false.
Finally: return p = NULL; is this just a shorthand for:
p = NULL;
return p;
Yes.
Upvotes: 1