Skip to content

Instantly share code, notes, and snippets.

@jesseschalken
Last active September 7, 2018 08:42
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save jesseschalken/87108ec4a392ecd408bddd85dfae74bb to your computer and use it in GitHub Desktop.
Save jesseschalken/87108ec4a392ecd408bddd85dfae74bb to your computer and use it in GitHub Desktop.
export class CircularBuffer<T> implements Iterable<T> {
private start: number = 0;
private _length: number = 0;
private array: T[] = [];
grow(size: number) {
if (size > this.array.length) {
size = Math.max(size, this.array.length * 1.5);
const array = new Array<T>(size | 0);
for (const x of this) {
array.push(x);
}
this.array = array;
}
}
get(index: number) {
return this.array[this.offset(index)];
}
set(index: number, value: T) {
this.array[this.offset(index)] = value;
}
private offset(index: number) {
index = (index + this.start) % this.array.length;
if (index < 0) {
index += this.array.length;
}
return index;
}
push(value: T) {
if (this.start + this.length == this.array.length) {
this.array.push(value);
} else {
this.grow(this.length + 1);
this.set(this.length, value);
}
this._length++;
}
pop() {
let value;
if (this.start + this.length == this.array.length) {
value = this.array.pop();
} else {
value = this.get(this.length - 1);
this.set(this.length - 1, undefined as any);
}
this._length--;
return value;
}
unshift(value: T) {
this.grow(this.length + 1);
this.set(-1, value);
this.start = this.offset(-1);
}
shift() {
const value = this.get(0);
this.set(0, undefined as any);
this.start++;
return value;
}
get length() {
return this._length;
}
*[Symbol.iterator]() {
for (let i = 0; i < this.length; i++) {
yield this.get(i);
}
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment