What I am trying to achieve is somewhat like a radio group behavior, where only one radio input can be selected at a time. For example, the starting array [0, 1, 1, 1, 1, 1] should have its elements swapped in the following way:
| index | array |
|---|---|
0 |
[0, 1, 1, 1, 1, 1] |
1 |
[1, 0, 1, 1, 1, 1] |
2 |
[1, 1, 0, 1, 1, 1] |
3 |
[1, 1, 1, 0, 1, 1] |
4 |
[1, 1, 1, 1, 0, 1] |
5 |
[1, 1, 1, 1, 1, 0] |
I have come up with this, but I think it does "extra work" (unnecessary loops) in certain scenarios.
function rearrange(array: number[], idx: number) {
let arr = array.slice();
let l = arr.length;
if (arr.indexOf(0) === idx) return arr;
while (arr.indexOf(0) !== idx) {
let swap;
for (let i = 0; i < l; i ) {
if (arr[i] === 0 || arr[i 1] === 0) {
swap = arr[i];
if (i 1 < l) {
arr[i] = arr[i 1];
arr[i 1] = swap;
}
if (i 1 > l) {
arr[i] = arr[i - 1];
arr[i - 1] = swap;
}
}
}
}
return arr;
}
I was wondering if you would have ideas on how to make this process simpler/better.
CodePudding user response:
Just identify the previous 0 with findIndex, assign 1 to it, and assign 0 to the idx?
function rearrange(array: number[], idx: number) {
const arr = [...array];
arr[arr.indexOf(0)] = 1;
arr[idx] = 0;
return arr;
}
Another approach...
const rearrange = (array: number[], idx: number) => (
array.map((_, i) => i === idx ? 0 : 1)
);
CodePudding user response:
Instead of swapping pairs, you can rotate the subarray in "one go", using slice and splice.
Here is a function that does the job, mutating the given array (not returning a new one), together with a sequence of calls to demonstrate it. I assume values could be varying and need to stay together as if they were swapped with the "moving" 0:
function rearrange(array, idx) {
let zero = array.indexOf(0);
if (zero < idx) {
arr.splice(zero, idx - zero 1, ...arr.slice(zero 1, idx 1), 0);
} else {
arr.splice(idx, zero - idx 1, 0, ...arr.slice(idx, zero));
}
}
arr = [0,1,2,3,4,5];
rearrange(arr, 3);
console.log(...arr);
rearrange(arr, 1);
console.log(...arr);
rearrange(arr, 5);
console.log(...arr);
rearrange(arr, 1);
console.log(...arr);
