d4rkb1ue d4rkb1ue - 7 months ago 34
Javascript Question

JavaScript Array.prototype.sort() CAN NOT call on DOM.HTMLLIElements

I want to use

Array.prototype.sort()
to sort DOM.Element.

I try like this:



var e = document.getElementById('test-list').children;

[].forEach.call(e,function(ee){
console.log(ee);
});
// print each child in e

[].sort.call([3,4,1],function(a,b){
console.log(a+","+b);
});
// 3,4; 4,1; [3, 4, 1]; compares every two elements


[].sort.call(e,function(a,b){
console.log(a+","+b);
});
// CAN NOT work! don't print anything.

<ol id="test-list">
<li class="lang">Scheme</li>
<li class="lang">JavaScript</li>
<li class="lang">Python</li>
<li class="lang">Ruby</li>
<li class="lang">Haskell</li>
</ol>





Base on API of
Array.prototype.sort()
,
sort()
can be used on normal Objects more than basic type.

And I found

e[0].innerText = 232; // <li class="lang">232</li> ;works
e[0] = "123"; //<li class="lang">232</li> ;not work


So I assumed because of the fact that elements in Array of HTMLLIElements can not be changed directly,
sort()
somehow figured it out. So
sort()
just jump out and return.

Is that right? And what's the institution helps
sort()
decide whether deal with the Array?

Answer

Interesting question! Unlike Chrome, which dies silently, the latest Firefox is more helpful:

TypeError: HTMLCollection doesn't have an indexed property setter for '0'

which makes the problem clear: you cannot apply sort to an object that doesn't have numeric property setters (because sort attempts to sort in place and fails).