Mark Bell Mark Bell - 3 months ago 7
HTML Question

Why does Array.concat produce a three element array when concatenating a two-element and three-element array of jQuery objects?

I have a form with two fixed input elements, followed by any number of dynamically created elements which will all have name attribute values suffixed with the same string (see snippet). I am trying to arrive at an array of jQuery objects, one for each of those input elements.

However, it seems that when I concatenate a 2-element array containing the objects representing the first two elements and a 3-element array containing the objects for the rest of the elements, the result is just an array containing the first array's objects, with just one extra element containing the second array's objects as an array, which is not how I understood

concat
to work.

I would expect the new array to be a five-element array containing jQuery objects representing the first two fixed inputs, followed by the rest.

Ignoring whether this is the right approach to the problem at hand (it most likely isn't): is my expectation wrong, and can someone explain why
concat
produces this result?



var firstTwoFields = [
$('[name=field1]'),
$('[name=field2]')
];

var otherFields = $('[name$=test]').map(function() { return $(this); });

var newArray = firstTwoFields.concat(otherFields);

document.write('firstTwoFields.length: ' + firstTwoFields.length + '<br>');
document.write('otherFields.length: ' + otherFields.length + '<br>');
document.write('newArray.length: ' + newArray.length + '<br>');
document.write('newArray[2].length: ' + newArray[2].length + '<br>');

<script src="https://ajax.googleapis.com/ajax/libs/jquery/1.11.1/jquery.min.js"></script>

<input name="field1" value="" /><br>
<input name="field2" value="" /><br>
<input name="field3_test" value="" /><br>
<input name="field4_test" value="" /><br>
<input name="field5_test" value="" /><br>
<br>




Answer

$().map() will return jQuery object that is array like and has a length, but isn't a proper array that you can use Array.prototype methods on.

You need to use get() to return a proper array, or use $.map():

var otherFields = $('[name$=test]').map(function() { return $(this); }).get();

Using $.map():

 var otherFields = $.map( $('[name$=test]'), function(elem) { return $(elem); })

Reference: get() docs