public void TestReadmeExample0() { int binCount = 3; Tally <float> tally = new Tally <float>(binCount, x => (int)(x * binCount)); // Some where, this is called repeatedly. // tally.Add(neuron.value); // But let's supply some fake values for demonstration purposes. tally.Add(0.2f); tally.Add(0.1f); tally.Add(0.4f); tally.Add(0.5f); // Finally we analyze it. float[] p = tally.probability; Assert.Equal(new [] { 2 / 4f, 2 / 4f, 0f }, p); float H = ProbabilityDistribution.Entropy(p); // Here's the entropy without any normalization. Assert.Equal(0.7f, H, 1); // Let's use a base of 2 so the entropy is in the units of bits. float Hbits = ProbabilityDistribution.Entropy(p, 2); Assert.Equal(1f, Hbits, 1); // So this neuron's value carries one bit of information. It's either going // into the first bin or the second bin at an equal probability and never // going into the third bin. }
static Tally GetTally(List <CalcExpression> p, bool numbersOnly) { var tally = new Tally(numbersOnly); foreach (CalcExpression e in p) { tally.Add(e); } return(tally); }
public void TestReadmeExample1() { int binCount = 4; Tally <float, float> tally = new Tally <float, float>(binCount, x => (int)(x * binCount), binCount, y => (int)(y * binCount)); // Some where, this is called repeatedly. // tally.Add(sensor.value, effector.value); // But let's supply some fake values for demonstration purposes. tally.Add(0.6f, 0.1f); tally.Add(0.5f, 0.5f); tally.Add(0.7f, 0.9f); tally.Add(0.7f, 0.3f); // Finally we analyze it. float[] px = tally.probabilityX; Assert.Equal(new [] { 0f, 0f, 1f, 0f }, px); float[] py = tally.probabilityY; Assert.Equal(new [] { 1 / 4f, 1 / 4f, 1 / 4f, 1 / 4f }, py); float[,] pxy = tally.probabilityXY; Assert.Equal(new [, ] { { 0f, 0f, 0f, 0f }, { 0f, 0f, 0f, 0f }, { 1 / 4f, 1 / 4f, 1 / 4f, 1 / 4f }, { 0f, 0f, 0f, 0f }, }, pxy); float Hsensor = ProbabilityDistribution.Entropy(px, 2); float Heffector = ProbabilityDistribution.Entropy(py, 2); // H(effector | sensor) float Heffector_sensor = ProbabilityDistribution.ConditionalEntropyYX(pxy, px, 2); Assert.Equal(0f, Hsensor, 1); // So the sensor carries no information. It's going to the second bin always // based on what's been seen. Assert.Equal(2f, Heffector, 1); // The effector carries 2 bits of information. It could show up in any of // the bins with equal probability. It would take two bits to describe which bin. Assert.Equal(2f, Heffector_sensor, 1); // Given that we know the sensor, there's no reduction in randomness for the // effector. In fact since H(effector) = H(effector|sensor) we now know that // the sensor and effector are entirely independent of one another. }
private TraceItem StartTrace(TraceKind kind, PatternElement source) { TraceItem traceElement = new TraceItem { Kind = kind, PatternElement = source, State = TraceState.InProgress }; Items.Add(traceElement); if (!Tally.TryGetValue(source, out TallyEntry entry)) { entry = new TallyEntry { LastPosition = 0, Count = 0 }; Tally.Add(source, entry); } if (entry.LastPosition != State.Enumerator.Index) { entry.Count = 0; entry.LastPosition = State.Enumerator.Index; } entry.Count++; if (entry.Count > CycleThreshold) { throw new Exception("Possible cycle detected!"); } return(traceElement); }
private static object Sum(List<Expression> p) { var tally = new Tally(); foreach (var e in p) { tally.Add(e); } return tally.Sum(); }