Skip to content

Instantly share code, notes, and snippets.

@BenDMyers
Created December 5, 2020 18:25
Show Gist options
  • Save BenDMyers/455925c7bb9f531041a88e803291d034 to your computer and use it in GitHub Desktop.
Save BenDMyers/455925c7bb9f531041a88e803291d034 to your computer and use it in GitHub Desktop.
Declarative implementation of Array.prototype.splice
/**
* Simplified `splice` implementation that doesn't handle all the different use cases for `start`.
*
* Deleting items in-place without using `splice` is hard. Here's the plan:
* 1. Create an array (`deletedItems`) of items which the user WANTS to remove from the array.
* 2. Create an array (`reinsertedItems`) of all items that come AFTER the deleted items.
* 3. Truncate the whole array to everything UP TO `start`.
* 4. Insert any new items provided by the user.
* 5. Reinsert everything in `reinsertedItems`.
* 6. Return `deletedItems`.
*
* @param {number} start index to start deleting/inserting at
* @param {number} [deleteCount] how many items to delete
* @param {...any} [itemsToInsert] items to insert into the array at `start`
* @returns {Array} array of deleted items, or an empty array if no items were deleted.
*/
Array.prototype._splice = function(start, deleteCount, ...itemsToInsert) {
let deletedItems = [];
let reinsertedItems = [];
// Parameter setup
if (!Number.isInteger(deleteCount)) {
deleteCount = this.length - start;
}
let i = start;
// 1. Create an array (`deletedItems`) of items which the user WANTS to remove from the array.
for (; i < start + deleteCount; i++) {
deletedItems.push(this[i]);
}
// 2. Create an array (`reinsertedItems`) of all items that come AFTER the deleted items.
for (; i < this.length; i++) {
reinsertedItems.push(this[i]);
}
// 3. Truncate the whole array to everything UP TO `start`.
this.length = start;
// 4. Insert any new items provided by the user
if (Array.isArray(itemsToInsert)) {
for (let j = 0; j < itemsToInsert.length; j++) {
this.push(itemsToInsert[j]);
}
}
// 5. Reinsert everything in `reinsertedItems`.
for (let k = 0; k < reinsertedItems.length; k++) {
this.push(reinsertedItems[k]);
}
// 6. Return `deletedItems`.
return deletedItems;
}
const fruits1 = ['Apple', 'Cherry', 'Banana', 'Plum', 'Tangerine', 'Watermelon'];
const removed1 = fruits1._splice(4);
console.log(fruits1, removed1);
const fruits2 = ['Apple', 'Cherry', 'Banana', 'Plum', 'Tangerine', 'Watermelon'];
const removed2 = fruits2._splice(4, 1);
console.log(fruits2, removed2);
const fruits3 = ['Apple', 'Cherry', 'Banana', 'Plum', 'Tangerine', 'Watermelon'];
const removed3 = fruits3._splice(2, 3, 'Peach', 'Nectarine');
console.log(fruits3, removed3);
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment