Skip to content
Permalink
Browse files

Make sure that empty nodelists continue to map properly. Fixes #8993.

  • Loading branch information...
jeresig committed May 2, 2011
1 parent 86aa764 commit 6c449fd5df3e0ec50e893d055da9aea486e7d71c
Showing with 8 additions and 2 deletions.
  1. +1 −1 src/core.js
  2. +7 −1 test/unit/core.js
@@ -720,7 +720,7 @@ jQuery.extend({
i = 0,
length = elems.length,
// jquery objects are treated as arrays
isArray = elems instanceof jQuery || length !== undefined && typeof length === "number" && ( ( length > 0 && elems[ 0 ] && elems[ length -1 ] ) || jQuery.isArray( elems ) ) ;
isArray = elems instanceof jQuery || length !== undefined && typeof length === "number" && ( ( length > 0 && elems[ 0 ] && elems[ length -1 ] ) || length === 0 || jQuery.isArray( elems ) ) ;

// Go through the array, translating each of the items to their
if ( isArray ) {
@@ -653,7 +653,7 @@ test("first()/last()", function() {
});

test("map()", function() {
expect(7);
expect(8);

same(
jQuery("#ap").map(function(){
@@ -694,6 +694,12 @@ test("map()", function() {
});
equals( mapped.length, scripts.length, "Map an array(-like) to a hash" );

var nonsense = document.getElementsByTagName("asdf");
var mapped = jQuery.map( nonsense, function( v, k ){
return v;
});
equals( mapped.length, nonsense.length, "Map an empty array(-like) to a hash" );

var flat = jQuery.map( Array(4), function( v, k ){
return k % 2 ? k : [k,k,k];//try mixing array and regular returns
});

18 comments on commit 6c449fd

@rkatic

This comment has been minimized.

Copy link
Contributor

replied May 2, 2011

The problem of simply adding length === 0 is that now even functions with no args (length == 0) will be traversed as arrays.
I know there is no such unit test (to add?), but $.each has.

@timmywil

This comment has been minimized.

Copy link
Member

replied May 2, 2011

@rkatic: I'm not sure what you mean. Passing a function to map?

@kflorence

This comment has been minimized.

Copy link

replied May 2, 2011

So I guess John isn't in favor of isArrayLike either?

@rkatic

This comment has been minimized.

Copy link
Contributor

replied May 2, 2011

@timmywil: Yes. Like in $.each.

@kflorence: Maybe because of number of lines?

@timmywil

This comment has been minimized.

Copy link
Member

replied May 2, 2011

Not trying to be difficult, but you mean iterate a function? A code example would help me understand.

Also, we tabled isArrayLike for 1.7. I'm not sure John's had time to review the matter.

@rkatic

This comment has been minimized.

Copy link
Contributor

replied May 2, 2011

Yes. For example $.map( MyClass, handleStatics ).

EDIT: Probably not a big deal. Probably I am just a consistency-freak...

@timmywil

This comment has been minimized.

Copy link
Member

replied May 2, 2011

Hmm, I don't think that's a valid use case either for map or for each. I think iterating an instance(as in the case of a jQuery object) would be workable, but not a raw function.

@rkatic

This comment has been minimized.

Copy link
Contributor

replied May 2, 2011

$.each does supports iterating functions. Just look in $.each code and you will see isObj = length === undefined || jQuery.isFunction( object );.
Also there is a respective unit test for $.each.

@timmywil

This comment has been minimized.

Copy link
Member

replied May 2, 2011

OK. I thought you were suggesting there was a regression in map.

@rkatic

This comment has been minimized.

Copy link
Contributor

replied May 2, 2011

As I said, probably I am just a consistency-freak...

and for that I am glad that isArrayLike will be considered. :)

@timmywil

This comment has been minimized.

Copy link
Member

replied May 2, 2011

fair enough :)

@kflorence

This comment has been minimized.

Copy link

replied May 2, 2011

As I said, probably I am just a consistency-freak...
and for that I am glad that isArrayLike will be considered. :)

Me too. Glad to hear it will be considered in 1.7!

@jboesch

This comment has been minimized.

Copy link
Contributor

replied May 3, 2011

I'm kinda glad this is consistent. I know we don't say that jQuery.map supports node lists in the docs, but we had a unit test in core.js that mapped through node lists. This should have either been removed from the unit tests (if we chose not to support node lists) or added support to empty node lists.

@rkatic

This comment has been minimized.

Copy link
Contributor

replied May 3, 2011

@jboesch: Rarely you can say that a documentation is also a specification for something. First one is generally a more user-friendly version of the second.
In case of jQuery, documentation is certainly not the specification. Is it needed? Maybe, but it is not simple in case of jQuery... but unit tests are pretty close.

EDIT: Also, i think NodeList are also objects. Why you think it have to be explicitly mentioned to be supported?

@jboesch

This comment has been minimized.

Copy link
Contributor

replied May 3, 2011

@rkatic: The docs are the only specification there is at the moment (that I'm aware of). All I'm sayin' is that I think jQuery should either support node lists and go all out (which means handling the empty node lists properly and documenting it), or don't support node lists at all.

@rkatic

This comment has been minimized.

Copy link
Contributor

replied May 3, 2011

As I updated my previous comment: Why NodeLists have to be explicitly mentioned if those are also objects?

@jboesch

This comment has been minimized.

Copy link
Contributor

replied May 3, 2011

A node list looks like an object, but technically, it's a node list (with an item method).
You're right about being able to handle them like objects though. Maybe it doesn't need to be documented. shrug

@rkatic

This comment has been minimized.

Copy link
Contributor

replied May 3, 2011

For users, it probably don't have to be mentioned (it's a documentation). For developers there are unit tests (+docs) :)

Please sign in to comment.
You can’t perform that action at this time.