アシアルブログ

アシアルの中の人が技術と想いのたけをつづるブログです

配列の奥底にある値をもとに配列をソートする

こんにちは。松田です。
書くことが思いつかなかったので今回は軽めのネタをひとつ。
php連想配列を扱っている時、配列の奥深くにある値をもと配列全体をソートしたい場合があります。
そんなときに使える方法の紹介です。

たとえばこんな配列。


<?php

$list = array(
  array('data' => array('data2' => array('value' => 111))),
  array('data' => array('data2' => array('value' => 444))),
  array('data' => array('data2' => array('value' => 333))),
  array('data' => array('data2' => array('value' => 222))),
  array('data' => array('data2' => array('value' => 555))),
);

?>

かなり極端に書いてますが、この配列を value の値でソートしたいとします。

完成後の理想型がこちら。


<?php

$list = array(
  array('data' => array('data2' => array('value' => 111))),
  array('data' => array('data2' => array('value' => 222))),
  array('data' => array('data2' => array('value' => 333))),
  array('data' => array('data2' => array('value' => 444))),
  array('data' => array('data2' => array('value' => 555))),
);

?>



こんな場合は、usortとcreate_functionで次のように書きましょう。



<?php

usort($list, create_function('$a,$b', 'return $a["data"]["data2"]["value"] > $b["data"]["data2"]["value"];'));

?>

実行後 print_r($list) はこんな感じになります。



Array
(
    [0] => Array
        (
            [data] => Array
                (
                    [data2] => Array
                        (
                            [value] => 111
                        )

                )

        )

    [1] => Array
        (
            [data] => Array
                (
                    [data2] => Array
                        (
                            [value] => 222
                        )

                )

        )

    [2] => Array
        (
            [data] => Array
                (
                    [data2] => Array
                        (
                            [value] => 333
                        )

                )

        )
長いので以下省略。。


みごとvalueの順に昇順にソートされてますね。


なんとなく予想がつくかもしれませんが、降順にソートする場合は判定式の不等号を逆にしちゃいましょう。



<?php

usort($list, create_function('$a,$b', 'return $a["data"]["data2"]["value"] > $b["data"]["data2"]["value"];'));

?>


実行結果。



Array
(
    [0] => Array
        (
            [data] => Array
                (
                    [data2] => Array
                        (
                            [value] => 555
                        )

                )

        )

    [1] => Array
        (
            [data] => Array
                (
                    [data2] => Array
                        (
                            [value] => 444
                        )

                )

        )
以下略。。



php5.3以降の場合は無名関数も使えるので、下記のようにかくこともできます。



<?php

$func = function($a, $b) { 
	return $a["data"]["data2"]["value"] > $b["data"]["data2"]["value"];
};
usort($list, $func);

?>


判定処理部分をすべて文字列で書かなければいけないcreate_functionよりはこちらのほうがカッコよく書けますね。
こんなふうにusortとcreate_functionは相性がよくなかなか使えます。


・・・とここまで書いたのですが、array_multisortという関数で同じようなことができるようです。。なんてこったい\(^o^)/
お好きな方をどうぞ。。