export class RingBuffer { private values = new DoublyLinkedList() private ignored = 0 constructor(readonly size: number, readonly ignoreFn?: Predicate) {} push(value: T) { if (this.values.length - this.ignored >= this.size) { this.values.shift() } this.values.add(value) if (this.ignoreFn && this.ignoreFn(value)) { this.ignored++ } return this.values } pop() { const popped = this.values.pop() if (popped && this.ignoreFn && this.ignoreFn(popped)) { this.ignored-- } return this.values } toChunk(): Chunk { const chunk = Chunk.builder() this.values.forEach((t) => { chunk.append(t) }) return chunk.build() } toChunkReversed(): Chunk { return Chunk.from(this.toChunk().reverse) } }