sort()での昇順と降順に並び替えるときのメモ【jQuery】

sort()って、なんか時たま怪しい挙動しますよね。 配列に格納している値を昇順や降順やらでsortするときに、微妙にハマったのでそのの処理のメモです。

ことの発端

JSでブロックレベル要素の高さを揃えるという処理はよくするかと思うのですが、該当するブロックレベル要素の高さをすべて取得して、一番数値のでかいのを、それぞれの高さに指定するというものです。簡単なソースコードだと下記のような感じになるかと思います。

$(function() {
	var self = $(".foo");
	var hList = [];
	for(var i = 0; i < self.length; i++) {
		hList.push(self.eq(i).height());
	}
	var hList = hList.sort();
	var hMax = hList[0];
	self.height(hMax);
});

狙いとしては、取得した高さを降順に並び替えるとhListの配列の最初の値が一番でかい数値になるので、それをそれぞれの高さにするというものです。

今回遭遇したのが、上記のコードで、動くことは動いたのですが、動かない場合もありました。動かなくて当たり前といえば当たり前で、sort()で、降順や昇順で並び変えるときには、sort()の引数に比較関数を入れなければならないからです。

なので下記のように書き加え。
var funcList = {
	descend  : function(a,b){ return b - a; }
};

$(function() {
	var self = $(".foo");
	var hList = [];
	for(var i = 0; i < self.length; i++) {
		hList.push(self.eq(i).height());
	}
	var hList = hList.sort(funcList.descend);
	var hMax = hList[0];
	self.height(hMax);
});

降順への並び替えの関数を追加し、それをsort()の引数に指定することによってちゃんと動作し、一番高い数値の高さにこれでなります。

謎が謎を呼ぶ(謎)

上記のことで動作するのですが、動作しないという意味不明なケースに遭遇しました。原因はよく分かりません。なので、下記のように降順にする関数を変更

var funcList = {
	descend : function(a,b){ return (parseInt(a) < parseInt(b)) ? 1 : -1; }
};

比較関数のリストを作る

sort()が結構不安定だという話はどこかで聞いたことがあるのですが、sort()のせいなのか、自分の書き方が変なのか(どっちも当てはまりそうなのでアレ(ナニ)ですが)。

というわけで(謎)、降順やら昇順の処理は下記のような感じで使うようにしています。

var funcList = {
	ascend   : function(a,b){ return a-b; },
	ascend2  : function(a,b){ return (parseInt(a) > parseInt(b)) ? 1 : -1; },
	descend  : function(a,b){ return b-a; },
	descend2 : function(a,b){ return (parseInt(a) < parseInt(b)) ? 1 : -1; }

};

sort()の引数で使う場合は、下記のような感じで書いてもらえばOKです。

var funcList = {
	ascend   : function(a,b){ return a-b; },
	ascend2  : function(a,b){ return (parseInt(a) > parseInt(b)) ? 1 : -1; },
	descend  : function(a,b){ return b-a; },
	descend2 : function(a,b){ return (parseInt(a) < parseInt(b)) ? 1 : -1; }

};

//昇順1
hoge.sort(funcList.ascend);

//昇順2
hoge.sort(funcList.ascend2);

//降順
hoge.sort(funcList.descend);

//降順2
hoge.sort(funcList.descend2);