# How to split a long array into smaller arrays, with JavaScript

I have an array of e-mails (it can be just 1 email, or 100 emails), and I need to send the array with an ajax request (that I know how to do), but I can only send an array that has 10 or less e-mails in it. So if there is an original array of 20 e-mails I will need to split them up into 2 arrays of 10 each. or if there are 15 e-mails in the original array, then 1 array of 10, and another array of 5. I'm using jQuery, what would be the best way to do this?

Don't use jquery...use plain javascript

``````var a = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15];

var b = a.splice(0,10);

//a is now [11,12,13,14,15];
//b is now [1,2,3,4,5,6,7,8,9,10];
``````

You could loop this to get the behavior you want.

``````var a = YOUR_ARRAY;
while(a.length) {
console.log(a.splice(0,10));
}
``````

This would give you 10 elements at a time...if you have say 15 elements, you would get 1-10, the 11-15 as you wanted.

``````var size = 10; var arrayOfArrays = [];
for (var i=0; i<bigarray.length; i+=size) {
arrayOfArrays.push(bigarray.slice(i,i+size));
}
console.log(arrayOfArrays);
``````

Unlike `splice()`, `slice()` is non-destructive to the original array.

Just loop over the array, splicing it until it's all consumed.

``````

var a = ['a','b','c','d','e','f','g']
, chunk

while (a.length > 0) {

chunk = a.splice(0,3)

console.log(chunk)

}

``````

output

``````
[ 'a', 'b', 'c' ]
[ 'd', 'e', 'f' ]
[ 'g' ]

``````

Assuming you don't want to destroy the original array, you can use code like this to break up the long array into smaller arrays which you can then iterate over:

``````var longArray = [];   // assume this has 100 or more email addresses in it
var shortArrays = [], i, len;

for (i = 0, len = longArray.length; i < len; i += 10) {
shortArrays.push(longArray.slice(i, i + 10));
}

// now you can iterate over shortArrays which is an
// array of arrays where each array has 10 or fewer
// of the original email addresses in it

for (i = 0, len = shortArrays.length; i < len; i++) {
// shortArrays[i] is an array of email addresss of 10 or less
}
``````

As a supplement to @jyore's answer, and in case you still want to keep the original array:

``````var originalArray = [1,2,3,4,5,6,7,8];

var splitArray = function (arr, size) {

var arr2 = arr.slice(0),
arrays = [];

while (arr2.length > 0) {
arrays.push(arr2.splice(0, size));
}

return arrays;
}

splitArray(originalArray, 2);
// originalArray is still = [1,2,3,4,5,6,7,8];
``````

Another method:

``````var longArray = [1, 2, 3, 4, 5, 6, 7, 8, 9, 10];
var size = 2;

var newArray = new Array(Math.ceil(longArray.length / size)).fill("")
.map(function() { return this.splice(0, size) }, longArray.slice());

// newArray = [[1, 2], [3, 4], [5, 6], [7, 8], [9, 10]];
``````

This doesn't affect the original array as a copy, made using slice, is passed into the 'this' argument of map.

Array.reduce could be inefficient for large arrays, especially with the mod operator. I think a cleaner (and possibly easier to read) functional solution would be this:

``````const chunkArray = (arr, size) =>
arr.length > size
? [arr.slice(0, size), ...chunkArray(arr.slice(size), size)]
: [arr];
``````

More compact:

``````const chunk = (xs, size) =>
xs.map((_, i) =>
(i % size === 0 ? xs.slice(i, i + size) : null)).filter(Boolean);

// Usage:
const sampleArray = new Array(33).fill(undefined).map((_, i) => i);

console.log(chunk(sampleArray, 5));``````

If you want a method that doesn't modify the existing array, try this:

``````let oldArray = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15];
let newArray = [];
let size = 3; // Size of chunks you are after
let j = 0; // This helps us keep track of the child arrays

for (var i = 0; i < oldArray.length; i++) {
if (i % size === 0) {
j++
}
if(!newArray[j]) newArray[j] = [];
newArray[j].push(oldArray[i])
}
``````

You can use lodash: https://lodash.com/docs

``````_.chunk(['a', 'b', 'c', 'd'], 2);
// ? [['a', 'b'], ['c', 'd']]
``````

Another implementation:

``````const arr = ["H", "o", "w", " ", "t", "o", " ", "s", "p", "l", "i", "t", " ", "a", " ", "l", "o", "n", "g", " ", "a", "r", "r", "a", "y", " ", "i", "n", "t", "o", " ", "s", "m", "a", "l", "l", "e", "r", " ", "a", "r", "r", "a", "y", "s", ",", " ", "w", "i", "t", "h", " ", "J", "a", "v", "a", "S", "c", "r", "i", "p", "t"];

const size = 3;
const res = arr.reduce((acc, curr, i) => {
if ( !(i % size)  ) {    // if index is 0 or can be divided by the `size`...
acc.push(arr.slice(i, i + size));   // ..push a chunk of the original array to the accumulator
}
return acc;
}, []);

// => [["H", "o", "w"], [" ", "t", "o"], [" ", "s", "p"], ["l", "i", "t"], [" ", "a", " "], ["l", "o", "n"], ["g", " ", "a"], ["r", "r", "a"], ["y", " ", "i"], ["n", "t", "o"], [" ", "s", "m"], ["a", "l", "l"], ["e", "r", " "], ["a", "r", "r"], ["a", "y", "s"], [",", " ", "w"], ["i", "t", "h"], [" ", "J", "a"], ["v", "a", "S"], ["c", "r", "i"], ["p", "t"]]
``````

NB - This does not modify the original array.

Or, if you prefer a functional, immutable and self-contained method:

``````function splitBy(size, list) {
return list.reduce((acc, curr, i, self) => {
if ( !(i % size)  ) {
return [
...acc,
self.slice(i, i + size),
];
}
return acc;
}, []);
}
``````

I would like to share my solution as well. It's a little bit more verbose but works as well.

``````var data = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15];

var chunksize = 4;

var chunks = [];

data.forEach((item)=>{
if(!chunks.length || chunks[chunks.length-1].length == chunksize)
chunks.push([]);

chunks[chunks.length-1].push(item);
});

console.log(chunks);
``````

Output (formatted):

``````[ [ 1,  2,  3,  4],
[ 5,  6,  7,  8],
[ 9, 10, 11, 12],
[13, 14, 15    ] ]
``````

Another implementation, using Array.reduce (I think it’s the only one missing!):

``````const splitArray = (arr, size) =>
{
if (size === 0) {
return [];
}

return arr.reduce((split, element, index) => {
index % size === 0 ? split.push([element]) : split[Math.floor(index / size)].push(element);
return split;
}, []);
};
``````

As many solutions above, this one’s non-destructive. Returning an empty array when the size is 0 is just a convention. If the `if` block is omitted you get an error, which might be what you want.

You can take a look at this code . Simple and Effective .

``````function chunkArrayInGroups(array, unit) {
var results = [],
length = Math.ceil(array.length / unit);

for (var i = 0; i < length; i++) {
results.push(array.slice(i * unit, (i + 1) * unit));
}
return results;
}

chunkArrayInGroups(["a", "b", "c", "d"], 2);
``````

Here is a simple one liner

``````var segment = (arr, n) => arr.reduce((r,e,i) => i%n ? (r[r.length-1].push(e), r)
: (r.push([e]), r), []),
arr = Array.from({length: 31}).map((_,i) => i+1);
console.log(segment(arr,7));``````

``````function chunkArrayInGroups(arr, size) {
var newArr=[];

for (var i=0; arr.length>size; i++){
newArr.push(arr.splice(0,size));
}
newArr.push(arr.slice(0));
return newArr;

}

chunkArrayInGroups([0, 1, 2, 3, 4, 5, 6], 3);
``````
``````function chunkArrayInGroups(arr, size) {
var newArr=[];

for (var i=0; i < arr.length; i+= size){
newArr.push(arr.slice(i,i+size));
}
return newArr;

}

chunkArrayInGroups([0, 1, 2, 3, 4, 5, 6], 3);
``````

as a function

``````var arrayChunk = function (array, chunkSize) {
var arrayOfArrays = [];

if (array.length <= chunkSize) {
arrayOfArrays.push(array);
} else {
for (var i=0; i<array.length; i+=chunkSize) {
arrayOfArrays.push(array.slice(i,i+chunkSize));
}
}
return arrayOfArrays;
}
``````

to use

``````arrayChunk(originalArray, 10) //10 being the chunk size.
``````

using recursion

``````let myArr = [1,2,3,4,5,6,7,8,9,10,11,12,13,14,15,16];
let size = 4; //Math.sqrt(myArr.length); --> For a n x n matrix
let tempArr = [];
function createMatrix(arr, i) {
if (arr.length !== 0) {
if(i % size == 0) {
tempArr.push(arr.splice(0,size))
}
createMatrix(arr, i - 1)
}
}
createMatrix(myArr, myArr.length);
console.log(tempArr);
``````

Note: The existing array i.e. myArr will be modified.

using prototype we can set directly to array class

``````Array.prototype.chunk = function(n) {
if (!this.length) {
return [];
}
return [this.slice(0, n)].concat(this.slice(n).chunk(n));
};
console.log([1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13, 14, 15].chunk(5));``````