InterlockedExchange гарантирует, что изменение переменной и возврат ее исходного значения не будут прерваны другими потоками.
Итак, если 'i' является целым числом, эти вызовы (взятые по отдельности) не требуют InterlockedExchange вокруг 'i':
a = i;
i = 9;
i = a;
i = a + 9;
a = i + 9;
if(0 == i)
Ни одно из этих утверждений не полагается на ОБА начальные И конечные значения 'i'. Но эти следующие вызовы действительно требуют InterlockedExchange вокруг 'i':
a = i++; //a = InterlockedExchange(&i, i + 1);
Без этого два потока, проходящие через один и тот же код, могут получить одинаковое значение «i», присвоенное «a», или «a» может неожиданно пропустить два или более числа.
if(0 == i++) //if(0 == InterlockedExchange(&i, i + 1))
Два потока могут выполнить код, который должен произойти только один раз.
и т.д.