Web系のこととかー。

多次元配列の中のキーでソート

$lists = array(
	array(
		'id' => 1,
		'name' => 'a',
	),
	array(
		'id' => 2,
		'name' => 'b',
	),
	array(
		'id' => 3,
		'name' => 'c',
	),
	array(
		'id' => 4,
		'name' => 'd',
	),
);

多次元配列で、idをキーに降順でソート

usort($lists, create_function('$a,$b','return($b[\'id\'] - $a[\'id\']);'));

多次元配列で、nameをキーに昇順でソート

usort($lists, create_function('$a,$b','return($a[\'name\'] - $b[\'name\']);'));

usort()を使えばユーザ定義比較関数を使うことができるので、階層の深い多次元配列でもソート可能。

array_multisort()を使う

array_multisort() は本当に便利な関数で、上記と同じことをができる。

$keys = array();
foreach ($lists as $val) $keys[] = $val['name'];
array_multisort($keys, SORT_DESC, $lists);

usort() と array_multisort() の実行速度を比較

apacheのabでパフォーマンスを比較したところ、僕の環境下では array_multisort() の方が、usort() よりも5倍早かった。

連想インデックスを保持しつつソート

$lists = array(
	'a' => array(
		'id' => 1,
		'name' => 'a',
	),
	'b' => array(
		'id' => 2,
		'name' => 'b',
	),
	'c' => array(
		'id' => 3,
		'name' => 'c',
	),
	'd' => array(
		'id' => 4,
		'name' => 'd',
	),
);

連想配列で、idをキーに降順でソート(連想インデックスを保持)

uasort($lists, create_function('$a,$b','return($b[\'id\'] - $a[\'id\']);'));

連想インデックスでソート

$lists = array(
	'safari' => array(
		'id' => 1,
	),
	'ie' => array(
		'id' => 2,
	),
	'firefox' => array(
		'id' => 3,
	),
	'chrome' => array(
		'id' => 4,
	),
	'opera' => array(
		'id' => 5,
	),
);

(多次元)配列で、連想インデックスを降順でソート(連想インデックスを保持)

krsort($lists);
//ksort()が昇順

下記の uksort() を使えば、この場合は krsort() と同じ結果に。

uksort($lists, create_function('$a,$b','return(strcasecmp($b,$a));'));

uksort() を使うメリットとしては、やはりユーザ定義比較関数が使えるので、PHPマニュアルにあるように下記のようなことができる。

function cmp($a, $b){
	$a = preg_replace('@^(a|an|the) @', '', $a);
	$b = preg_replace('@^(a|an|the) @', '', $b);
	return strcasecmp($a, $b);
}

$a = array("John" => 1, "the Earth" => 2, "an apple" => 3, "a banana" => 4);

uksort($a, "cmp");

日付・時刻でソート

$lists = array(
	array(
		'id' => 1,
		'date' => '2011-01-01 12:00:00',
	),
	array(
		'id' => 2,
		'date' => '2010-12-01 12:00:00',
	),
	array(
		'id' => 3,
		'date' => '2011-02-01 12:00:00',
	),
	array(
		'id' => 4,
		'date' => '2009-01-01 12:00:00',
	),
);

strtotime() でタイムスタンプに変換して比較することもできる。便利。

usort($lists, create_function('$a,$b','return(strtotime($a[\'date\']) > strtotime($b[\'date\']));'));
§284 · 1月 18, 2011 · プログラミング_PHP · · [Print]

Leave a Reply