2012-07-30 2 views
1

정렬 방향에 문제가 있습니다. 방향을 가지고 다차원 배열을 정렬하려고합니다. 나는 얼마나 많은 매개 변수가 될지 모르기 때문에 array_multisort()을 직접 사용할 수 없습니다. 내가 사용 call_user_func_array('array_multisort', $params); 그리고 그것은 작동하지만, 정렬 방향 (SORT_ASC,SORT_DESC)를 설정할 수 없습니다. call_user_func_array('array_multisort', $params);의 정렬 방향을 어떻게 설정할 수 있습니까? 여기 내 코드는, 당신이call_user_func_array with array_multisort

function get_fields($data, $order_by) { 
    $order_row = preg_split("/[\s,]+/", $order_by); 
    for ($i=0;$i<count($order_row);$i++) { 
     foreach ($data as $key => $row) { 
      $tmp[$i][$key] = $row[$order_row[$i]];  
     } 
    } 
    return $tmp; 
} 

function ordering($data, $order_by) { 
    $tmp = get_fields($data, $order_by); 
    $params = array(); 
    foreach($tmp as &$t){ 
     $params[] = &$t; 
    } 

    $params[1] = array("SORT_DESC","SORT_DESC","SORT_DESC","SORT_DESC"); // like that no warning but no sorting 

    $params[] = &$data; 
    call_user_func_array('array_multisort', $params); 
    return array_pop($params); 
} 

$data = array (
    array('id' => 1,'name' => 'Barack','city' => 9), 
    array('id' => 7,'name' => 'boris','city' => 2), 
    array('id' => 3,'name' => 'coris','city' => 2), 
    array('id' => 3,'name' => 'coris','city' => 2) 
); 

$order_by = "city desc, name"; 

echo "<br>ORDER BY $order_by<br>"; 
$ordered = ordering($data, $order_by); 
echo "<pre>"; 
var_dump($ordered); 
echo "</pre>"; 

내가 MySQL을 ORDER BY city DESC, name 같은 종류의 작업을 수행하려는 시도 할 수 있습니다. 내 목표 야.

답변

1

같은 비교 기능을 한 번 정렬 할 수 있습니다. call_user_func_array()가 상수를 처리 할 수없는 것 같습니다. 나는 동적으로이 문자열 인수의 캐릭터 라인을 구축하고 평가하여이 문제를 해결했습니다

$args = array($arr1, $arr2); 
$order = array(SORT_ASC, SORT_DESC); 
$evalstring = ''; 

foreach($args as $i=>$arg){ 
    if($evalstring == ''){ $evalstring.= ', '; } 
    $evalstring.= '$arg'; 
    $evalstring.= ', '.$order[$i]; 
} 
eval("array_multisort($evalstring);"); 

나는 (평가 알고는) 악이 깨끗한 방법이 아니다, 그러나 그것은 ;-)

를 작동
0

배열을 여러 번 정렬하고 ORDER BY city DESC, name ASC과 같은 결과를 얻으려면 stable sort을 수행하는 함수가 필요합니다.
는 지금까지 내가 PHP 하나가없는 알고 그래서 당신은 내가 같은 문제가 있었이

$data = array (
    array('id' => 3,'name' => 'coris','city' => 2), 
    array('id' => 1,'name' => 'Barack','city' => 9), 
    array('id' => 7,'name' => 'boris','city' => 2), 
    array('id' => 3,'name' => 'coris','city' => 2), 
); 

$order_by = array(
    'city' => array('dir' => SORT_DESC, 'type' => SORT_NUMERIC), 
    'name' => array('dir' => SORT_ASC, 'type' => SORT_STRING), 
); 

function compare($row1,$row2) { 
    /* this function should determine which row is greater based on all of the criteria 
     and return a negative number when $row1 < $row2 
        a positive number when $row1 > $row2 
        0 when $row1 == $row2 
    */ 

    global $order_by; 

    foreach($order_by as $field => $sort) { 
     if($sort['type'] != SORT_NUMERIC) { 
      // strings are compared case insensitive and assumed to be in the mb_internal_encoding 
      $cmp = strcmp(mb_strtolower($row1[$field]), mb_strtolower($row2[$field])); 
     } else { 
      $cmp = doubleval($row1[$field]) - doubleval($row2[$field]); 
     } 
     if($sort['dir'] != SORT_ASC) $cmp = -$cmp; 
     if($cmp != 0) return $cmp; 
    } 
    return 0; 
} 


usort($data,'compare');