It took me a little bit to figure this out. The behavior of "+=" is unintuitive here. I normally wouldn't come across this because I don't program this way.
However, I could tell from the beginning that statefulness was the underlying cause of this (As it is the underlying cause of nearly all problems in life).
Let's look at a really simplified version of that reproduces the problem:
flist = {0, 0, 0};
Do[
flist[[1 + RandomVariate[BinomialDistribution[2, 0.5]]]] +=1,
{10000}]
Note that I had to add one to the index since arrays are indexed from 1 to 3 instead of 0 to 2.
Why does this cause the problem? Let's use Trace to look at the heart of the Do loop with a flist set to {0,0,0}:
flist[[1 + RandomVariate[BinomialDistribution[2, 0.5]]]] +=1//Trace
{flist[[1+RandomVariate[BinomialDistribution[2,0.5]]]]++,{{flist,{0,0,0}},{{RandomVariate[BinomialDistribution[2,0.5]],
{BinomialDistribution[2,0.5][RandomType],RandomInteger},1},1+1,2},{0,0,0}[[2]],0},
{flist[[1+RandomVariate[BinomialDistribution[2,0.5]]]]=1,1},0}
What does this mean? What has happened? RandomVariate is called twice. Not once.
First, RandomVariate is called to get the value from flist. That value is incremented by 1. Then, RandomVariate is called again. This time to give a position of where to assign the new value.
The end result is that values are largely swapped just swapped with each other. If you wanted to program this the way you have, you would use With to hold onto the value:
flist = {0, 0, 0};
Do[
With[{rndval = 1 + RandomVariate[BinomialDistribution[2, 0.5]]},
flist[[rndval]] += 1],
{10000}]
A Shorter Explanation
x += 1
is defined as being the same as x = x + 1
. So:
flist[[1 + RandomVariate[BinomialDistribution[2, 0.5]]]] +=1
is really just syntatic sugar for:
flist[[1 + RandomVariate[BinomialDistribution[2, 0.5]]]] = flist[[1 + RandomVariate[BinomialDistribution[2, 0.5]]]] + 1
This operation takes a random value from the list, adds one to it, and then puts that value randomly back into the list somewhere.