Lab
Dynamic array
// A teaching model of a growing array. In real code, use your language's own:
// a TypeScript array, a Go slice, a Rust Vec.
class GrowingArray {
slots: (number | undefined)[] = new Array(4).fill(undefined);
length = 0;
/** Entries copied, shifted or written: the work this lesson counts. */
moves = 0;
get capacity(): number {
return this.slots.length;
}
append(value: number): void {
if (this.length === this.capacity) {
// Full: copy every entry into a buffer twice the size, then use it.
const oldSlots = this.slots;
const newSlots: (number | undefined)[] = new Array(oldSlots.length * 2).fill(undefined);
for (let i = 0; i < this.length; i++) {
newSlots[i] = oldSlots[i];
this.moves++;
}
this.slots = newSlots;
}
this.slots[this.length] = value;
this.length++;
this.moves++;
}
get(index: number): number | undefined {
return index >= 0 && index < this.length ? this.slots[index] : undefined;
}
remove(index: number): number | undefined {
if (index < 0 || index >= this.length) return undefined;
const removed = this.slots[index];
// Keep the order: move every later entry one place earlier.
for (let i = index + 1; i < this.length; i++) {
this.slots[i - 1] = this.slots[i];
this.moves++;
}
this.length--;
this.slots[this.length] = undefined;
return removed;
}
values(): number[] {
return this.slots.slice(0, this.length) as number[];
}
}
const results = new GrowingArray();
for (const bib of [12, 7, 31, 4]) results.append(bib);
const beforeFifth = results.moves;
results.append(19);
const fifthAppend = results.moves - beforeFifth;
console.log(`five: ${results.values().join(", ")} | capacity ${results.capacity} | fifth append ${fifthAppend} moves`);
const beforeRemove = results.moves;
const removed = results.remove(1);
const removal = results.moves - beforeRemove;
console.log(`removed ${removed}: ${results.values().join(", ")} | capacity ${results.capacity} | ${removal} moves`);
console.log(`index 1 now: ${results.get(1)}`);
TODO
Visual to come