public ulong Insert(HistogramBucket hb, ulong count) { bool found; int idx; if (bvs == null) { bvs = new HistogramBucketPair[DEFAULT_HIST_SIZE]; allocd = DEFAULT_HIST_SIZE; } found = InternalFind(hb, out idx); if (!found) { if (used == allocd) { /* A resize is required */ HistogramBucketPair[] newbvs = new HistogramBucketPair[allocd + DEFAULT_HIST_SIZE]; if (idx > 0) { Array.Copy(bvs, 0, newbvs, 0, idx); } newbvs[idx].bucket = hb; newbvs[idx].count = count; newbvs[idx].bucket = hb; newbvs[idx].count = count; if (idx < used) { Array.Copy(bvs, idx, newbvs, idx + 1, used - idx); } bvs = newbvs; allocd += DEFAULT_HIST_SIZE; } else { // used !== alloced /* We need to shuffle out data to poke the new one in */ Array.Copy(bvs, idx, bvs, idx + 1, used - idx); bvs[idx].bucket = hb; bvs[idx].count = count; } used++; } else { // found /* Just need to update the counters */ ulong newval = bvs[idx].count + count; if (newval < bvs[idx].count) /* we rolled */ { newval = ulong.MaxValue; } count = newval - bvs[idx].count; bvs[idx].count = newval; } return(count); }
public Histogram(byte[] raw) { uint read = 0; ushort cnt = 0; allocd = used = 0; if (raw.Length < 2) { return; } cnt = (ushort)((ushort)raw[0] << 8); cnt |= (ushort)raw[1]; read = 2; HistogramBucketPair[] newbvs = new HistogramBucketPair[cnt]; for (ushort i = 0; i < cnt; i++) { if (raw.Length < read + 4) { return; } if (raw.Length < read + 4 + raw[read + 2]) { return; } newbvs[i].bucket = new HistogramBucket(true, unchecked ((sbyte)raw[read + 1]), unchecked ((sbyte)raw[read])); newbvs[i].count = 0; for (byte j = 0; j <= raw[read + 2]; j++) { newbvs[i].count = (newbvs[i].count << 8) | (ulong)raw[read + 3 + j]; } read += 4 + (uint)raw[read + 2]; } bvs = newbvs; allocd = used = cnt; }