I have array structured like this:
[
[8,[1]],
[15,[2]],
[20,[3]],
[23,[4,41]],
[497,[18]],
[1335,[38]],
[2092,[39,55,61]],
[3615,[5]],
[4121,[14]],
[5706,[39,55,61]],
[5711,[62]],
[5714,[63]],
[5719,[64]],
[6364,[38]]
]
I use the modified code from this answer to find consecutive numbers but I can't adapt it to also find consecutive numbers from arrays with multiple values
This is my code :
const a = [
[8,[1]],
[15,[2]],
[20,[3]],
[23,[4,41]],
[497,[18]],
[1335,[38]],
[2092,[39,55,61]],
[3615,[5]],
[4121,[14]],
[5706,[39,55,61]],
[5711,[62]],
[5714,[63]],
[5719,[64]],
[6364,[38]]
];
// this variable will contain arrays
let finalArray = [];
// Create a recursive function
function checkPrevNextNumRec(array) {
let tempArr = [];
// if the array contaon only 1 element then push it in finalArray and
// return it
if (array.length === 1) {
finalArray.push(array);
return
}
// otherside check the difference between current & previous number
for (let i = 1; i < array.length; i++) {
if (array[i][1][0] - array[i - 1][1][0] === 1) {
// if current & previous number is 1,0 respectively
// then 0 will be pushed
tempArr.push(array[i - 1]);
} else {
// if current & previous number is 5,2 respectively
// then 2 will be pushed
tempArr.push(array[i - 1])
// create a an array and recall the same function
// example from [0, 1, 2, 5, 6, 9] after removing 0,1,2 it
// will create a new array [5,6,9]
let newArr = array.splice(i);
finalArray.push(tempArr);
checkPrevNextNumRec(newArr)
}
// for last element if it is not consecutive of
// previous number
if (i === array.length - 1) {
tempArr.push(array[i]);
finalArray.push(tempArr)
}
}
}
checkPrevNextNumRec(a)
And here the result, as you can see, all the tables containing consecutive figures in [i][1][0]
have been grouped
[
[
[8,[1]],
[15,[2]],
[20,[3]],
[23,[4,41]]
],
[
[497,[18]]
],
[
[1335,[38]],
[2092, [39,55,61]]
],
[
[3615,[5]]
],
[
[4121,[14]]
],
[
[5706,[39,55,61]]
],
[
[5711,[62]],
[5714,[63]],
[5719,[64]]
],
[
[6364,[38]]
]
]
But I need that field 5706 is also included with 5711, 5714, and 5719, but obviously it is not included because is not in [i][1][0]
I thought of being inspired by this post but I cannot integrate it correctly
Can you help me?
Thanks!
You need to check the last element of the grouped value.
const array = [[8, [1]], [15, [2]], [20, [3]], [23, [4, 41]], [497, [18]], [1335, [38]], [2092, [39, 55, 61]], [3615, [5]], [4121, [14]], [5706, [39, 55, 61]], [5711, [62]], [5714, [63]], [5719, [64]], [6364, [38]]], grouped = array.reduce((r, a) => { var last = r[r.length - 1]; if (!last || last[last.length - 1][1][0] + 1 !== a[1][0]) r.push(last = []); last.push(a); return r; }, []); console.log(grouped);
.as-console-wrapper { max-height: 100% !important; top: 0; }
Basically the logic here is to iterate over the input
and at each iteration, compare it with the data values from the previous iteration ie: prevData
.
On each iteration, I used Array.prototype.map
to create a new array that contains the what-would-be consecutive values (relative to the data in the previous iteration) by simply adding 1 to each item in prevData
.
Next step is to loop that array to see if we encounter a consecutive value - as soon as we do we can break
as there's no need to keep checking.
Finally is we apply the grouping logic with a single if/else
.
const a = [ [8, [1]], [15, [2]], [20, [3]], [23, [4, 41]], [497, [18]], [1335, [38]], [2092, [39, 55, 61]], [3615, [5]], [4121, [14]], [5706, [39, 55, 61]], [5711, [62]], [5714, [63]], [5719, [64]], [6364, [38]] ]; function group(input) { let prev; return input.reduce((accum, el) => { let hasConsecutive = false; const [key, current] = el; if (prev == null) { prev = current; } const consecutives = prev.map(n => n + 1); for (let i = 0; i < consecutives.length; i += 1) { if (current.includes(consecutives[i])) { hasConsecutive = true; break; } } if (prev && hasConsecutive) { accum[accum.length - 1].push(el); } else { accum.push([el]); } prev = current; return accum; }, []); } console.log(group(a));
Here's the result run through a beautifier:
[
[
[8, [1]],
[15, [2]],
[20, [3]],
[23, [4, 41]]
],
[
[497, [18]]
],
[
[1335, [38]],
[2092, [39, 55, 61]]
],
[
[3615, [5]]
],
[
[4121, [14]]
],
[
[5706, [39, 55, 61]],
[5711, [62]],
[5714, [63]],
[5719, [64]]
],
[
[6364, [38]]
]
]
The following code enumerates each of the items in the array.
For each item, its sub-array is enumerated to see if the following item fits in a sequence.
If it fits in sequence, the next item is appended to a temporary variable, and we continue to the next item.
If the last entry in the subarray is reached without detecting a continuation of the sequence, we end the current sequence, start a new sequence and continue to the next item.
const data = [ [8,[1]], [15,[2]], [20,[3]], [23,[4,41]], [497,[18]], [1335,[38]], [2092,[39,55,61]], [3615,[5]], [4121,[14]], [5706,[39,55,61]], [5711,[62]], [5714,[63]], [5719,[64]], [6364,[38]] ] function sequences(data) { const result = [] let sequence = [data[0]] for(let x=0; x<data.length-1; x++) { const [,sub] = data[x] for(let y=0; y<sub.length; y++) { const currSubV = sub[y] const [,nextSub] = data[x+1] if(nextSub.some((nextSubV) => currSubV+1 === nextSubV)) { sequence.push(data[x+1]) break } if(y === sub.length-1) { result.push(sequence) sequence = [data[x+1]] } } } return result } for(let s of sequences(data)) console.log(JSON.stringify(s).replace(/\\s/g))
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.