4

次の配列があります

$records = array(

    array("postId"=>"1","grid"=>"6"),
    array("postId"=>"2","grid"=>"3"),
    array("postId"=>"3","grid"=>"6"),
    array("postId"=>"4","grid"=>"3"),
    array("postId"=>"5","grid"=>"3"),
    array("postId"=>"6","grid"=>"12"),
    array("postId"=>"7","grid"=>"3"),

);

任意の数の連続した「グリッド」の合計が 12 になるように、この配列を並べ替えたいと思います。

例: 上記の配列の「グリッド」の値は次のとおりです: 6,3,6,3,3,12,3

(6+6=12), (3+3+3+3=12),(12=12) したがって、新しい順序は6,6,3,3,3,3,12or3,3,3,3,12,6,6または6,3,3,6,3,3,12

したがって、配列をソートした後、新しい配列は次のようになります。

$records=array(

    array("postId"=>"1","grid"=>"6"),
    array("postId"=>"3","grid"=>"6"),
    array("postId"=>"2","grid"=>"3"),       
    array("postId"=>"4","grid"=>"3"),
    array("postId"=>"5","grid"=>"3"),
    array("postId"=>"7","grid"=>"3"),
    array("postId"=>"6","grid"=>"12"),

);

PHPマニュアルを検索したところ、次の関数が見つかりました:sort、uasort、uksort、usortですが、それらの使用方法がわかりませんでした。

PHP を使用してこれを実現する方法を教えてください。

アップデート

グリッドの値は常に 3 または 6 または 12 になります (これら 3 つの数値のみ)

問題

  $records = array(

    array("postId"=>"1","grid"=>"3"),
    array("postId"=>"2","grid"=>"6"),    
    array("postId"=>"3","grid"=>"3"),     
    array("postId"=>"4","grid"=>"3"),
    array("postId"=>"5","grid"=>"6"),
    array("postId"=>"6","grid"=>"6"),    
    array("postId"=>"7","grid"=>"3"),
    array("postId"=>"8","grid"=>"6"),

 );
4

4 に答える 4

4

したがって、実際にはソートしていませんが、並べ替えてシーケンスを作成しています。高さを固定したレンガのレイアウトをしようとしていて、各行を埋めて残りを最後に残すために並べ替える必要があると思います。与えられた固定バリアントでは12,6,3、降順でソートすることで実行できます。6 の数が奇数の場合、小さい 3 で埋められます。ただし、このような順序では退屈なレイアウトが作成されます。より興味深いものにするには、いくつかの投稿を並べ替えるだけで済みます。このためには、一時コンテナーを作成し、そのグリッドの合計が 12 に等しくなったときにマージする必要があります。いくつかの一時コンテナーが残っている場合は、それらを 1 つにマージし、降順で並べ替えてから、以前にグループ化したものとマージします。

私のコンセプトを示すコード:

//auxiliary function to calculate sum of grids in given temporary container
    function reduc($a) {
    return array_reduce($a, function ($result, $item) {
        return $result . $item['grid'] . ',';
    }, '');
}

function regroup($records, $group_sum = 12) {
    $temp = array();
    $grouped = array();

    foreach ($records as $r) {
        if ($r['grid'] == $group_sum) {
            $grouped[] = $r;
        } else {
            if (!$temp) {
                $temp[] = array($r);
            } else {
                $was_grouped = false;
                foreach ($temp as $idx => $container) {
                    $current_sum = sum_collection($container);
                    if ($current_sum + $r['grid'] <= $group_sum) {
                        $temp[$idx][] = $r;
                        if ($current_sum + $r['grid'] == $group_sum) {
                            $grouped = array_merge($grouped, $temp[$idx]);
                            unset($temp[$idx]);
                        }
                        $was_grouped = true;
                        break;
                    }
                }
                if (!$was_grouped) {
                    $temp[] = array($r);
                }
            }
        }
    }

    if ($temp) {
        //Sort descending, so biggest ones will be filled first with smalller
        $rest = call_user_func_array('array_merge', $temp);
        usort($rest, function($a, $b) {
            return $b['grid'] - $a['grid'];
        });
        $grouped = array_merge($grouped, $rest);
    }

    return $grouped;
}
于 2013-09-24T23:10:57.800 に答える
0

usort()PHP >= 5.3.0 では、クロージャー (またはハックとしてグローバル) を使用してこれを行うことができます。与えられた$records

$running_length = 0;
usort( $records, function( $a, $b ) use( $running_length ) {
    $running_length += $a["grid"];
    if( $running_length >= 12 ) return( true );
    return( false );
});

「グリッド」パラメーターを文字列の長さとして視覚化すると、最終結果 は$records次のように並べられます。

...            3
...            3
......         6
...                3
......             6
...                3
............  12

利用可能なチャンクのランダム性を考えると、最初にこの配列を最小から最大の順に並べ替えてから、適切に配置されるかどうかを確認することができます。このメソッドは明らかに、適合しない、または適合するように解決できない断片化やブロックを検出しません。

于 2013-09-24T20:19:01.740 に答える