I have an advanced report, which ultimately sorts the items based on your score:
// Variável $relatório contém dados levantados e calculados em blocos para N itens. Cada bloco possui uma pontuação total do mesmo.
// Ex: $relatorio[0]['consolidado']['bloco_1']['total_pontos'], $relatorio[0]['consolidado']['bloco_2']['total_pontos'], $relatorio[0]['consolidado']['bloco_3']['total_pontos'], $relatorio[0]['consolidado']['bloco_N']['total_pontos'], ...
$classificacao_items = array();
foreach ($relatorio as $relatorio_item) {
$classificacao_items[] = array(
'cod_item' => $relatorio_item['item']['cod_item'],
'item' => $relatorio_item['item']['descricao'],
'etapa_num' => $relatorio_item['consolidado']['etapa_num'], // etapa_num é um índice do relatório consolidado que recebe um valor de 0 a 5 (varia de acordo com média de metas atingidas do item)
'pontos' => $relatorio_item['consolidado']['total_pontos'],
);
}
Currently, I raise the sorting using multisort of the array
$classificacao_items = array_orderby($classificacao_items, 'etapa_num', SORT_ASC, 'pontos', SORT_DESC, 'item', SORT_ASC);
As you can see, I first sort by etapa_num
, then by pontos
and last by item
(Item name, alphabetical).
Function snippet:
/**
* Função de ordenação de arrays
* @see http://www.php.net/manual/en/function.array-multisort.php#100534
* @return mixed
*/
function array_orderby() {
$args = func_get_args();
$data = array_shift($args);
foreach ($args as $n => $field) {
if (is_string($field)) {
$tmp = array();
foreach ($data as $key => $row)
$tmp[$key] = $row[$field];
$args[$n] = $tmp;
}
}
$args[] = &$data;
call_user_func_array('array_multisort', $args);
return array_pop($args);
}
What I need now: If there is a tie of points, I need to examine the sum of blocks (1 and 2 in the case) of the items and give a better ranking for an item (adding blocks 1 and 2), since the current parameter would be his name. That is: you would need to apply a custom function.
My problem is that I can not successfully apply this custom function. It ends up detonating the organization of items already correctly classified.
// Variável $items == variável $relatorio (descrito acima na introdução), ou seja, apenas com outro "apelido"
usort($classificacao_items, function($a, $b) use ($items) {
if ($a['pontos'] != $b['pontos']) // na lógica quando retorna 0 não é pra modificar a posição do item
return 0;
$relatorio_a = $items[$a['cod_item']]['consolidado'];
$relatorio_b = $items[$b['cod_item']]['consolidado'];
$notas_a = $relatorio_a['bloco_1']['total_pontos'] + $relatorio_a['bloco_2']['total_pontos'];
$notas_b = $relatorio_b['bloco_1']['total_pontos'] + $relatorio_b['bloco_2']['total_pontos'];
return $notas_a > $notas_b ? 1 : -1;
});
At the moment, I can not see a workable solution to my problem. Every approach I try, I end up disorganizing with the order of the array. I need to apply this tiebreaker function only in cases where the punctuation is the same and does not change what is right (with more or less punctuation).