Sort php multidimensional array by key value - php

I have the below multidimesional array.
Array
(
[2] => Array
(
[66] => Array
(
[id] => 66
[count] => 9
)
[255] => Array
(
[id] => 255
[count] => 20
)
)
[1] => Array
(
[59] => Array
(
[id] => 59
[count] => 14
)
[255] => Array
(
[id] => 255
[count] => 73
)
)
)
I want to sort the inner array by value of count key in descending order.
How can I achieve it ?
Thanks.

try below solution:
<?php
$array = Array
(
'2' => Array
(
'66' => Array
(
'id' => 66 ,
'count' => 9
),
'255' => Array
(
'id' => 255,
'count' => 20
)
),
'1' => Array
(
'59' => Array
(
'id' => 59,
'count' => 14
),
'255' => Array
(
'id' => 255,
'count' => 73
)
)
);
echo '<pre>';
foreach($array as &$ar){
usort($ar, function($a, $b) {
return $b['count'] - $a['count'];
});
}
print_r($array);
Output:
Array
(
[2] => Array
(
[0] => Array
(
[id] => 255
[count] => 20
)
[1] => Array
(
[id] => 66
[count] => 9
)
)
[1] => Array
(
[0] => Array
(
[id] => 255
[count] => 73
)
[1] => Array
(
[id] => 59
[count] => 14
)
)
)

Here is an example:
Sort Multi-Dimensional Array By Value In PHP
https://paulund.co.uk/sort-multi-dimensional-array-value

Related

How to convert single array to multidimensional and group base on value name

for some reason i find hard to do single array to multidimensional
Im looking to group same filter_group_id with their filters like that
if filter_group_id is same as previews do
array[0][group_name] = > group_name, filter_group_id
then put all filters for same group in array like this
array[0][filters][] = > name, filter_id
for example i have single array like this one
Array
(
[0] => Array
(
[filter_group_id] => 43
[group_name] => price
[filter_id] => 62
[name] => 10 - 50
)
[1] => Array
(
[filter_group_id] => 43
[group_name] => price
[filter_id] => 64
[name] => 100 - 150
)
[2] => Array
(
[filter_group_id] => 33
[group_name] => size
[filter_id] => 52
[name] => 20m
)
[3] => Array
(
[filter_group_id] => 33
[group_name] => size
[filter_id] => 51
[name] => 10m
)
[4] => Array
(
[filter_group_id] => 32
[group_name] => color
[filter_id] => 49
[name] => red
)
[5] => Array
(
[filter_group_id] => 31
[group_name] => height
[filter_id] => 44
[name] => 90
)
)
and i like to become like this one
Array
(
[0] => Array
(
[group_name] => Array
(
[name] => price
[filter_group_id] => 43
)
[filters] => Array
(
[0] => Array
(
[filter_id] => 62
[name] => 10 - 50
)
[1] => Array
(
[filter_id] => 63
[name] => 50 - 100
)
)
)
[1] => Array
(
[group_name] => Array
(
[name] => size
[filter_group_id] => 33
)
[filters] => Array
(
[0] => Array
(
[filter_id] => 52
[name] => 20m
)
[1] => Array
(
[filter_id] => 51
[name] => 10m
)
)
)
[2] => Array
(
[group_name] => Array
(
[name] => color
[filter_group_id] => 32
)
[filters] => Array
(
[0] => Array
(
[filter_id] => 49
[name] => red
)
)
)
[3] => Array
(
[group_name] => Array
(
[name] => height
[filter_group_id] => 31
)
[filters] => Array
(
[0] => Array
(
[filter_id] => 46
[name] => 90
)
)
)
)
What i tried is this but thie coming in separaated arrays
$new_name = '';
$old_name = '';
$i = 0;
foreach ($query->rows as $key => $value) {
$new_name = $value['group_name'];
if ($new_name != $old_name) {
$data[$i] = array(
'group_name' => array(
'name' => $value['group_name'],
'filter_group_id' => $value['filter_group_id']
),
'filters' => array(
'name' => $value['name'],
'filter_id' => $value['filter_id']
)
);
$i++;
}else {
$data[$i] = array(
'group_name' => array(
'name' => $value['group_name'],
'filter_group_id' => $value['filter_group_id']
),
'filters' => array(
'name' => $value['name'],
'filter_id' => $value['filter_id']
)
);
}
$old_name = $value['group_name'];
}
You can use array_reduce to group your array based on the group_name and filter_group_id values, making a key for the result array based on those two values and adding the matching filter values to the filters subarray for each key. You can then use array_values to re-index the result array numerically:
$result = array_reduce($data, function ($c, $v) {
$key = $v['group_name'] . '#' . $v['filter_group_id'];
if (!isset($c[$key])) {
$c[$key] = array('group_name' => array('group_name' => $v['group_name'], 'filter_group_id' => $v['filter_group_id']));
}
$c[$key]['filters'][] = array('filter_id' => $v['filter_id'], 'name' => $v['name']);
return $c;
}, array());
$result = array_values($result);
print_r($result);
The output is too long to show here but matches your requirement.
Demo on 3v4l.org

Sort a multidimensional an array with numeric keys but keep the keys same just change the order [duplicate]

This question already has an answer here:
PHP sort associative array by numeric key in asc order [duplicate]
(1 answer)
Closed 10 months ago.
So I have 3 dimensional array. I want that array to be reordered based on the keys but the value of the keys should remain as it is. Like for an example if the array keys are 5,2,4,1,3 then it should become 1,2,3,4,5. Below I'm providing the array I have and excepted array and the solutions I have tried.
This is the array I have :-
[5] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => E3
[deal_text] =>
[units] => 5
[total_units] => 5
[amount] => 2620.8333333333
[is_freezed] =>
[can_sell] => 1
)
)
)
[2] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => E4
[deal_text] =>
[units] => 1
[total_units] => 0
[amount] => 516.66666666667
[is_freezed] => 1
[can_sell] =>
)
)
)
[4] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => C8
[deal_text] =>
[units] => 1
[total_units] => 0
[amount] => 526.66666666667
[is_freezed] => 1
[can_sell] =>
)
)
)
[1] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => D4
[deal_text] =>
[units] => 1
[total_units] => 0
[amount] => 557.14285714286
[is_freezed] => 1
[can_sell] =>
)
)
)
[3] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => E5
[deal_text] =>
[units] => 1
[total_units] => 0
[amount] => 516.66666666667
[is_freezed] => 1
[can_sell] =>
)
)
)
Following are the solutions I have tried :-
$result = ksort($result);
$result = array_values($result);
$result = array_splice($result, 0, 0);
$result = sort($result);
$result = array_splice($result, 0, count($result));
This is the expected array :-
Array
(
[1] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => D4
[deal_text] =>
[units] => 1
[total_units] => 0
[amount] => 557.14285714286
[is_freezed] => 1
[can_sell] =>
)
)
)
[2] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => E4
[deal_text] =>
[units] => 1
[total_units] => 0
[amount] => 516.66666666667
[is_freezed] => 1
[can_sell] =>
)
)
)
[3] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => E5
[deal_text] =>
[units] => 1
[total_units] => 0
[amount] => 516.66666666667
[is_freezed] => 1
[can_sell] =>
)
)
)
[4] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => C8
[deal_text] =>
[units] => 1
[total_units] => 0
[amount] => 526.66666666667
[is_freezed] => 1
[can_sell] =>
)
)
)
[5] => Array
(
[Anfield] => Array
(
[0] => Array
(
[slot] => E3
[deal_text] =>
[units] => 5
[total_units] => 5
[amount] => 2620.8333333333
[is_freezed] =>
[can_sell] => 1
)
)
)
)
Nothing is working any help will be appreciated. thanks in advance.
You are using ksort as $result = ksort($result);, ksort return TRUE/FALSE. That means you are assigning that to $results.
Read here PHP ksort
Your code should be:-
ksort($results);
instead of
$result = ksort($result);
You can use ksort for the keys sorting, here is an example
$arr = [
5 => [1,3],
3 => [2,3],
2 => [0,7]
];
ksort($arr);
echo '<pre>';
print_r($arr);
Output
Array
(
[2] => Array
(
[0] => 0
[1] => 7
)
[3] => Array
(
[0] => 2
[1] => 3
)
[5] => Array
(
[0] => 1
[1] => 3
)
)

How to format multi dimensional arrays as in a given format

I have an array with some keys, here what I need is to merge values at same keys e.g., scorecard value for key 117 & 107 should merged as given below in the output array.
$input_array = array (
38 => array
(
117 => array
(
'scorecard' => array
(
0 => 'q4'
),
'business_plan' => array
(
0 => 'q4'
)
),
107 => array
(
'scorecard' => array
(
0 => 'q1'
),
'business_plan' => array
(
0 => 'q2'
)
),
),
53 => array
(
373 => array
(
'scorecard' => array
(
0 => 'q4'
),
'business_plan' => array
(
0 => 'q1'
)
),
110 => array
(
'scorecard' => array
(
0 => 'q4',
0 => 'q3'
),
'business_plan' => array
(
0 => 'q4'
),
'marketing_plan' => array
(
0 => 'q3',
1 => 'q4'
)
)
),
318 => array
(
2279 => array
(
'scorecard' => array
(
0 => 'q4'
)
)
)
);
Output array will contain values like this:-
Array
(
[38] => Array
(
[scorecard] => Array
(
[0] => q4
[1] => q1
)
[business_plan] => Array
(
[0] => q4
[1] => q2
)
)
[53] => Array
(
[scorecard] => Array
(
[0] => q4
[1] => q3
)
[business_plan] => Array
(
[0] => q1
[0] => q4
)
[marketing_plan] => Array
(
[0] => q3
[1] => q4
)
)
[318] => Array
(
[scorecard] => Array
(
[0] => q4
)
)
)
It can be done by combining array_map, array_reduce and array_merge_recursive:
$result = array_map(function ($item) {
return array_reduce($item, 'array_merge_recursive', []);
}, $input_array);
Here is working demo.

Multidemensional array filter out duplicates within group

Im trying to remove the duplicate array value group based on the same dates(only keep 1 group).
Also take the number in the "1" key (above the pid key) and add it together with the duplicated grouped.
The issue im having is the each group under hour is "only" supposes to filter with duplicate groups under the same "hour" section.
Here's the array im starting with:
Array(
[1488] => Array
(
[hours] => Array
(
[0] => Array
(
[0] => 2016/07/11 - 2016/07/17
[1] => 37
[pid] => 1488
)
[1] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 51
[pid] => 1488
)
[2] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 44
[pid] => 1488
)
[3] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 22
[pid] => 1488
)
)
)
[2] => Array
(
[hours] => Array
(
[0] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 9.5
[pid] => 2
)
[1] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 8
[pid] => 2
)
[2] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 7
[pid] => 2
)
[3] => Array
(
[0] => 2016/07/11 - 2016/07/17
[1] => 5
[pid] => 2
)
)
)
)
Here what i need it to look like:
Array(
[0] => Array
(
[hours] => Array
(
[0] => Array
(
[0] => 2016/07/11 - 2016/07/17
[1] => 37
[pid] => 1488
)
[1] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 117
[pid] => 1488
)
)
)
[1] => Array
(
[hours] => Array
(
[0] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 24.5
[pid] => 2
)
[1] => Array
(
[0] => 2016/07/11 - 2016/07/17
[1] => 5
[pid] => 2
)
)
)
)
This is my code:
$temp_array = array();
$w = 0;
$key_array = array();
$new_array = array();
foreach($project_hours as $old_arrs) {
foreach ($old_arrs["hours"] as $val) {
if (!in_array($val[0], $key_array)) {
$key_array[$w] = $val[0];
$temp_array[$w] = $val;
} else {
$ser = array_search($val[0], $key_array);
$temp_array[$ser][1] += $val[1];
}
$w++;
$old_arrs["hours"] = $temp_array;
}
$new_array[] = $old_arrs;
}
echo '<pre>';
print_r($new_array);
echo '</pre>';
You can just do some simple tricks to organize the array keys, then use array_values() in two areas to reset the associative keys to numeric keys:
// Your array
$data = array(
1488 => array(
'hours' => array(
0 => array(
0 => '2016/07/11 - 2016/07/17',
1 => 37,
'pid' => 1488,
),
1 => array(
0 => '2016/07/04 - 2016/07/10',
1 => 51,
'pid' => 1488
),
2 => array(
0 => '2016/07/04 - 2016/07/10',
1 => 44,
'pid' => 1488
),
3 => array(
0 => '2016/07/04 - 2016/07/10',
1 => 22,
'pid' => 1488
)
)
),
2 => array(
'hours' => array(
0 => array(
0 => '2016/07/04 - 2016/07/10',
1 => 9.5,
'pid' => 2
),
1 => array(
0 => '2016/07/04 - 2016/07/10',
1 => 8,
'pid' => 2
),
2 => array(
0 => '2016/07/04 - 2016/07/10',
1 => 7,
'pid' => 2
),
3 => array(
0 => '2016/07/11 - 2016/07/17',
1 => 5,
'pid' => 2
)
)
)
);
// Loop through array...
foreach($data as $pid => $group) {
foreach($group['hours'] as $row) {
// I am using the date as a unique key so it's easy to organize
$new[$pid]['hours'][$row[0]][0] = $row[0];
// This will draw an warning if you don't first check that it's set
if(!isset($new[$pid]['hours'][$row[0]][1]))
$new[$pid]['hours'][$row[0]][1] = 0;
// Add values together as you go
$new[$pid]['hours'][$row[0]][1] += $row[1];
// On each loop this just assigns the pid (it just keeps overwriting itself
// but that is no big deal)
$new[$pid]['hours'][$row[0]]['pid'] = $pid;
}
// Here since you are not using date keys, just reset to numeric
$new[$pid]['hours'] = array_values($new[$pid]['hours']);
}
print_r(array_values($new));
Gives you:
Array
(
[0] => Array
(
[hours] => Array
(
[0] => Array
(
[0] => 2016/07/11 - 2016/07/17
[1] => 37
[pid] => 1488
)
[1] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 117
[pid] => 1488
)
)
)
[1] => Array
(
[hours] => Array
(
[0] => Array
(
[0] => 2016/07/04 - 2016/07/10
[1] => 24.5
[pid] => 2
)
[1] => Array
(
[0] => 2016/07/11 - 2016/07/17
[1] => 5
[pid] => 2
)
)
)
)

Compare values of two multidimentional array and insert if not exits

I have two array $array1 and $array2 which I get dynamically and look like
$array1 = Array
(
[0] => Array
(
[hour] => 10
[activity] => Array
(
[0] => Array
(
[activity_id] => 1
[cnt] => 2
)
[1] => Array
(
[activity_id] => 2
[cnt] => 1
)
)
)
[1] => Array
(
[hour] => 11
[activity] => Array
(
)
)
[2] => Array
(
[hour] => 12
[percentage] => 0
[activity] => Array
(
[0] => Array
(
[activity_id] => 2
[cnt] => 5
)
[1] => Array
(
[activity_id] => 3
[cnt] => 2
)
)
)
);
$array2 = Array
(
[0] => Array
(
[id] => 1
[name] => Phone Calls
[readable] => 1
[status] => active
)
[1] => Array
(
[id] => 2
[name] => Meeting With Customer
[readable] => 1
[status] => active
)
[2] => Array
(
[id] => 3
[name] => Others Works
[readable] => 1
[status] => active
)
);
which i need to compare.
if $array2['id'] is not in $array1["activity"](i.e"activity_id") add array ['activity_id'=>$array2['id'],'cnt'=>0] to $array1['activity'].
My result must be like
$result = Array
(
[0] => Array
(
[hour] => 10
[activity] => Array
(
[0] => Array
(
[activity_id] => 1
[cnt] => 2
)
[1] => Array
(
[activity_id] => 2
[cnt] => 1
)
[2] => Array
(
[activity_id] => 3
[cnt] => 0
)
)
)
[1] => Array
(
[hour] => 11
[activity] => Array
(
[0] => Array
(
[activity_id] => 1
[cnt] => 0
)
[1] => Array
(
[activity_id] => 2
[cnt] => 0
)
[2] => Array
(
[activity_id] => 3
[cnt] => 0
)
)
)
[2] => Array
(
[hour] => 12
[percentage] => 0
[activity] => Array
(
[0] => Array
(
[activity_id] => 1
[cnt] => 0
)
[1] => Array
(
[activity_id] => 2
[cnt] => 5
)
[2] => Array
(
[activity_id] => 3
[cnt] => 2
)
)
)
);
What i have tried is
$finalArray = array();
foreach($array1 as $arr1) {
foreach($array2 as $arr2) {
if(!in_array($arr2['id'], $arr1['activity'])) {
$array = ['activity_id'=>$arr2['id'], 'cnt'=>0];
}
array_push($arr1['activity'], $array);
unset($array);
}
array_push($finalArray, $result);
}
print_r($finalArray);
in_array() function is not working as I excepted or I am trying to do it in the wrong way. Can someone helps me with this?
Sorry,finally i get what i did wrong.May be someone get helped.
everything is ok just change the line
if(!in_array($arr2['id'], $arr1['activity'])) {
into
if(!in_array( $readActivity['id'], array_column($result['activity'],'activity_id'))){

Categories