[ about printf("%d", ++a, a + 5); ]
'++a' and 'a + 5' are separate expressions.
The value of 'a' is intact until the sequence point.
It looks like you are mistaken about the nature of sequence points.
A sequence point is a point in time where nothing happens,
a stability point, a point of rest. It is _not_ a point of action.
Transitions happen _between_ sequence points; at the sequence point
itself, the machine for a moment has come to a halt, all transitions
that happened before the sequence point have completed, and all
transitions that will happen after the sequence point have not yet started.
We could draw a timeline, like this:
activity rest activity rest activity
---------------+--------------------+--------------
seq seq
From what you write, it looks like you think that all the action
happens _at_ sequence points (sorry if I'm understanding you wrong).
In `` printf("%d", ++a, a + 5); '' the first sequence point, S0, is
before the statement starts. The next sequence point, S1, is before the
call to printf. In between those sequence points, the arguments
(the expressions ``"%d"'', ``++a'' and ``a+5'') are evaluated.
Several accesses to ``a'' will happen here: the ``a'' in ``++a''
will be read to obtain its previous value (event ar0),
the ``a'' in ``++a'' will be modified to store
the incremented value (event aw0) and ``a'' in ``a+5'' will be
read to compute the sum of ``a'' and ``5'' (event ar1).
Necessarily, ar0 must happen before aw0, because the value written
at aw0 depends on the value read at ar0. But ar1 can happen at any
time, so, the following interleavings are possible:
ar1,ar0,aw0
--+---------------+--
S0 S1
ar0,ar1,aw0
--+---------------+--
S0 S1
ar0,aw0,ar1
--+---------------+--
S0 S1
That's why the value of the third argument ``a+5'' is not well-defined.
It depends on the order in which aw0 and ar1 occur, and any order is
possible. In standardese: the variable ``a'' is both read and modified
between two sequence points, and the value is read (at ar1) for another
purpose than to compute the value written (at aw0).
When the write does not depend on the read, the implementation has
the freedom to schedule the read and the write in any order it wishes.