Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

For which use cases does Array.prototype.copyWithin() exist?

It is clear, how does the method work:

f = ['a','b','c','d','e','f','g','h'];

console.log(f.copyWithin(4,2,5));

//  copy elements between 2 (start) & 5 (end) -> to target -> 4  

//  [ 'a', 'b', 'c', 'd', 'e', 'f', 'g', 'h' ] <-- original array
//               ^    ^    ^
//               |    |    |                   <-- [2,5[ = c,d,e
//     0 -  1 -  2 -  3  - 4 -  5 -  6 -  7
//                         |    
//                        'c', 'd', 'e',       <-- copy to 4
//  [ 'a', 'b', 'c', 'd',  |    |    |   'h' ] <-- replace existing elements
//  [ 'a', 'b', 'c', 'd', 'c', 'd', 'e', 'h' ] <-- resulting array

But, why do I need such mechanism? For which use-cases?

like image 413
Lonely Avatar asked Dec 22 '17 21:12

Lonely


People also ask

What does copyWithin () function do?

The copyWithin() method copies array elements to another position in the array. The copyWithin() method overwrites the existing values. The copyWithin() method does not add items to the array.

What is the use of array prototype?

The Array.prototype.group() methods can be used to group the elements of an array, using a test function that returns a string indicating the group of the current element.

What is use of copyWithin in JavaScript?

copyWithin() The copyWithin() method shallow copies part of an array to another location in the same array and returns it without modifying its length.

What is the use of array prototype in JavaScript?

The JavaScript array prototype constructor is used to allow to add new methods and properties to the Array() object. If the method is constructed, then it will available for every array. When constructing a property, All arrays will be given the property, and its value, as default.


1 Answers

Here are some of use cases and very useful to use copyWithIn method.

  1. Implementing the Insertion Sort Algorithm.

const insertionSort = (data, compare) => {
  const arr = [...data];
  let unsort_index = 1;

  while (unsort_index < arr.length) {

    while (arr[unsort_index] >= arr[unsort_index - 1]) unsort_index += 1;
    const pick = arr[unsort_index];

    let iter = 0;
    while (iter < unsort_index && arr[iter] < pick) iter += 1;
    arr.copyWithin(iter + 1, iter, unsort_index);
    arr[iter] = pick;

    unsort_index += 1;
  }
  return arr;
}

const input = [2, 3, 5, 1, 9, 8, 6, 6];
const asc = (a, b) => a - b;
const dsc = (a, b) => b - a;

console.log({ input, asc_sorted: insertionSort(input, asc) });
console.log({ input, dsc_sorted: insertionSort(input, dsc) });
  1. Removing elements from array in place. (Checkout question 1, question 2)

function deleteItemsFromArray(array, delete_list) {
  for (let i = array.length - 1; i > -1; i--) {
    if (delete_list.includes(array[i])) {
      array.copyWithin(i, i + 1).pop();
    }
  }
}

// Alternate way, with minimal copy/move group of elements.
function deleteItemsFromArrayAlternate(array, delete_list) {
  let index = -1;
  let count = 0;
  for (let i = 0; i <= array.length; i++) {
    if (delete_list.includes(array[i]) || !(i in array)) {
      if (index > -1) {
        array.copyWithin(index - count + 1, index + 1, i);
      }
      count += 1;
      index = i;
    }
  }
  array.length = array.length - delete_list.length;
}

const array = [9, 12, 3, 4, 5, 6, 7];
deleteItemsFromArray(array, [9, 6, 7]);

console.log(array);
  1. Implementing custom encode. (Eg. Change spaces to %20 for given string in place).

const myEncode = (str) => {
  const arr = [...str];
  const num_of_spaces = arr.reduce(
    (count, c) => (c === " " ? count + 1 : count),
    0
  );
  arr.length += num_of_spaces * 3;
  for (let i = 0; i < arr.length; i++) {
    if (arr[i] === " ") {
      arr.copyWithin(i + 3, i + 1);
      arr[i] = "%";
      arr[i + 1] = "2";
      arr[i + 2] = "0";
    }
  }
  return arr.join("");
};

console.log(myEncode("this is some str"));
console.log(decodeURIComponent(myEncode("this is some str")));

PS: This code can be optimised if traverse from end to start.
  1. Rotating arrays. (Eg. left rotate by some number, right rotate by some number)

const arr = [1, 2, 3, 4, 5, 6];
// rotate to [3, 4, 5, 6, 1, 2];

const rotate = (arr, num) => {
  arr.length += num;
  arr.copyWithin(arr.length - num, 0, num);
  arr.copyWithin(0, num);
  arr.length -= num;
};

rotate(arr, 2)
console.log(arr);
like image 176
Siva K V Avatar answered Oct 06 '22 01:10

Siva K V