I'm having an array of three months which has Three Months Data and it holds Savings & Discount Information something like the below:
graphData holds the DataArr.
[DataArr] => Array
[0] => Array
(
[data] => Array
(
[0] => Array
(
[Month] => 10 Jan 2019
[Cost] => 60.3
[Name] => Savings
)
[1] => Array
(
[Month] => 10 Feb 2019
[Cost] => 45.3
[Name] => Savings
)
[2] => Array
(
[Month] => 10 Mar 2019
[Cost] => 50.6
[Name] => Savings
)
)
)
[1] => Array
(
[data] => Array
(
[0] => Array
(
[Month] => 10 Jan 2019
[Cost] => 89.62
[Name] => Discount
)
[1] => Array
(
[Month] => 10 Feb 2019
[Cost] => 20.2
[Name] => Discount
)
[2] => Array
(
[Month] => 10 Mar 2019
[Cost] => 0.0
[Name] => Discount
)
)
)
REQUIRED ARRAY - To Pass into Morris.js Line Chart
Now I want to iterate into this array and want to have the array format in a way as below
[data] => Array
(
[0] => Array
(
[Month] => 10 Jan 2019
[Savings] => 60.3
[Discount] => 89.62
)
[1] => Array
(
[Month] => 10 Feb 2019
[Saving] => 45.3
[Discount] => 20.2
)
[2] => Array
(
[Month] => 10 Mar 2019
[Saving] => 50.6
[Discount] => 0.0
)
)
Can you please share me how I can go about getting this into the required array using PHP? I tried array_push and other methods with JQuery Array methods as well, but all my efforts failed, and I'm working on this from past 3 days, any help is greatly appreciated.
Even tried with PHP foreach but even that failed, missing something and have no more ideas on how to get this working! Please let me know if any of you have much ideas on this.
Thanks
EDIT
**SAMPLE CODE I TRIED IN PHP **
for($k = 0; $k < sizeof($graphData['DataArr']); $k++ ) {
for($l = 0; $l < sizeof($graphData['DataArr'][$k]); $l++ ) {
array_push($graphData['DataArr'], array(
'label' => $graphData['DataArr'][$k][$l]['label'],
'percent' => $graphData['DataArr'][$k][$l]['percentage']
)
);
}
}
Here label => COST, DISCOUNT and Percentage is the value associated with the labels.
<?php
$graphData =
array(
'DataArr' =>
array
(
array(
'data' => array
(
array
(
'Month' => '10 Jan 2019',
'Cost' => 60.3,
'Name' => 'Savings'
),
array
(
'Month' => '10 Feb 2019',
'Cost' => 45.3,
'Name' => 'Savings'
),
array
(
'Month' => '10 Mar 2019',
'Cost' => 50.6,
'Name' => 'Savings'
)
)
),
array
(
'data' => array
(
array
(
'Month' => '10 Jan 2019',
'Cost' => 89.62,
'Name' => 'Discount'
),
array
(
'Month' => '10 Feb 2019',
'Cost' => 20.2,
'Name' => 'Discount'
),
array
(
'Month' => '10 Mar 2019',
'Cost' => 0.0,
'Name' => 'Discount'
)
)
)
)
);
$result = [];
foreach($graphData['DataArr'] as $value){
foreach($value['data'] as $details){
if(!isset($result['data'][$details['Month']])) $result['data'][$details['Month']] = ['Month' => $details['Month']];
$result['data'][$details['Month']][$details['Name']] = $details['Cost'];
}
}
$result['data'] = array_values($result['data']); // to eliminate keys
print_r($result);
Demo: https://3v4l.org/QMVuR
We first create a $result array with data key in it.
We loop over $graphData and store the values of Month,Savings and Discount under the indexed key value of Month.
In the end, we do array_values() to remove the keys.
Based on what you provided here is the code need to produce the new Array:
<?php
$data = [
[
'data' => [
[
'Month' => '10 Jan 2019',
'Cost' => 60.3,
'Name' => 'Savings'
],
[
'Month' => '10 Feb 2019',
'Cost' => 45.3,
'Name' => 'Savings'
],
[
'Month' => '10 Mar 2019',
'Cost' => 50.6,
'Name' => 'Savings'
]
],
],
[
'data' => [
[
'Month' => '10 Jan 2019',
'Cost' => 89.62,
'Name' => 'Discount'
],
[
'Month' => '10 Feb 2019',
'Cost' => 20.2,
'Name' => 'Discount'
],
[
'Month' => '10 Mar 2019',
'Cost' => 0.0,
'Name' => 'Discount'
]
],
]
];
$new_arr = ['data' => []];
echo "<pre>";
foreach( $data[0]['data'] as $key => $value) {
// $new_arr['data'][$k]['Month'] =
$new_arr['data'][$key]['Month'] = $value['Month'];
$new_arr['data'][$key]['Discount'] = $value['Cost'];
$new_arr['data'][$key]['Savings'] = $data[1]['data'][$key]['Cost'];
}
print_r($new_arr);
Note: this code assumes that $data array will only have 2 main elements, more elements in this array might might cause different behaviour.
Related
I have an array like below. There are id, label, cost, and cid in an array. We want to sum the cost based on the cid like for cid 22 cost should be 196.5 and for cid 11 cost should be 44.4. In our out put array we want to keep the label, cost (sum), and cid, Please see expected output array.
Array
(
[0] => Array
(
[id] => 1331
[label] => PM1
[cost] => 98.25
[cid] => 22
[product_id] => 133
)
[1] => Array
(
[id] => 1332
[label] => PM3
[cost] => 22.20
[cid] => 11
[product_id] => 133
)
[2] => Array
(
[id] => 1341
[label] => PM1
[cost] => 98.25
[cid] => 22
[product_id] => 134
)
[3] => Array
(
[id] => 1342
[label] => PM3
[cost] => 22.20
[cid] => 11
[product_id] => 134
)
)
Tried below
foreach ($array $key => $value) {
$final[$value['cid']] += $value['cost'];
}
print_r ($final);
Getting below as an output
Array
(
[22] => 196.5
[11] => 44.4
)
Want expected output like below.
Array
(
[22] => Array
(
[label] => PM1
[cost] => 196.5
[cid] => 22
)
[11] => Array
(
[label] => PM3
[cost] => 44.4
[cid] => 11
)
)
Basically want to sum cost based on cid and want to keep the label, cost (sum), and cid.
Any help will be greatly appreciated.
I believe this should do the trick
$CIDs_identified = array();
$final_array = array();
foreach($original_array as $small_array){
if(!in_array($small_array['cid'], $CIDs_identified)){
$CIDs_identified[] = $small_array['cid'];
$final_array[$small_array['cid']] = array(
'label' => $small_array['label'],
'cost' => $small_array['cost'],
'cid' => $small_array['cid'],
);
}else{
$final_array[$small_array['cid']]['cost'] += $small_array['cost'];
}
}
On this site, if you can provide your source array in usable format, that is really helpful so that we don't have to retype it. One way to do that is using var_export.
Below is a simple version. Create an array indexed by cid. If that item doesn't exist, populate it with the basic data and a zero cost. Then on each loop, including the initial, add the row's cost.
<?php
$data = [
[
'id' => 1331,
'label' => 'PMI',
'cost' => 98.25,
'cid' => 22,
'product_id' => 133,
],
[
'id' => 1341,
'label' => 'PMI',
'cost' => 98.25,
'cid' => 22,
'product_id' => 134,
],
];
$output = [];
foreach ($data as $item) {
if (!isset($output[$item['cid']])) {
$output[$item['cid']] = [
'label' => $item['label'],
'cost' => 0,
'cid' => $item['cid'],
];
}
$output[$item['cid']]['cost'] += $item['cost'];
}
print_r($output);
Demo here: https://3v4l.org/MY6Xu
$list = [
[ 'id' => 1331, 'label' => 'PM1', 'cost' => 98.25, 'cid' => 22, 'product_id' => 133 ],
[ 'id' => 1332, 'label' => 'PM3', 'cost' => 22.20, 'cid' => 11, 'product_id' => 133 ],
[ 'id' => 1341, 'label' => 'PM1', 'cost' => 98.25, 'cid' => 22, 'product_id' => 134 ],
[ 'id' => 1342, 'label' => 'PM3', 'cost' => 22.20, 'cid' => 11, 'product_id' => 134 ]
];
$result = [];
array_walk($list, function ($item) use (&$result) {
if (isset($result[$item['cid']])) {
$result[$item['cid']]['cost'] = $item['cost'] + $result[$item['cid']]['cost'];
} else {
$result[$item['cid']] = [ 'label' => $item['label'], 'cost' => $item['cost'], 'cid' => $item['cid'] ];
}
});
print_r($result);
Output:
Array
(
[22] => Array
(
[label] => PM1
[cost] => 196.5
[cid] => 22
)
[11] => Array
(
[label] => PM3
[cost] => 44.4
[cid] => 11
)
)
Hey All I have this object in php. that I want to sort by timestamp the array in variable $tempData
array (
0 =>
array (
'Timestamp' => '2022-02-21 06:00',
'Date' => '2022-02-21',
'Hour' => '06',
),
1 =>
array (
'Timestamp' => '2022-02-21 08:00',
'Date' => '2022-02-21',
'Hour' => '08',
),
2 =>
array (
'Timestamp' => '2022-02-21 03:00',
'Date' => '2022-02-21',
'Hour' => '03',
),
3 =>
array (
'Timestamp' => '2022-02-21 00:00',
'Date' => '2022-02-21',
'Hour' => '00',
),
)
I try this code from https://stackoverflow.com/questions/1597736/how-to-sort-an-array-of-associative-arrays-by-value-of-a-given-key-in-php
$sortedArray = array();
foreach ($tempData as $key => $row)
{
$sortedArray[$key] = $row['Timestamp'];
}
array_multisort($sortedArray, SORT_DESC, $tempData);
And the result is
[2022-02-21 05:26:30] local.INFO: The sorted data are:
[2022-02-21 05:26:30] local.INFO: array (
0 => '2022-02-21 06:00',
1 => '2022-02-21 08:00',
2 => '2022-02-21 03:00',
3 => '2022-02-21 00:00',
However I need all the origin array to be displayed, all the objects . meaning it will be the same object as $tempData with all the nodes, but sorted and not just to sort the field.
can someone advise?
I tried also this code:
function asc_sort_json($array1,$array2){
$on = 'Timestamp';
if ($array1[$on] == $array2[$on]) {
return 0;
}
return ($array1[$on] < $array2[$on]) ? -1 : 1;
}
usort($tempData, "asc_sort_json");
and get this error:
local.ERROR: usort() expects parameter 2 to be a valid callback, function 'asc_sort_json' not found or invalid function name {"exception":"[object] (ErrorException(code: 0): usort() expects parameter 2 to be a valid callback, function 'asc_sort_json' not found or invalid function name at
$tempData = [
[
'Timestamp' => '2022-02-21 06:00',
'Date' => '2022-02-21',
'Hour' => '06',
],
[
'Timestamp' => '2022-02-21 08:00',
'Date' => '2022-02-21',
'Hour' => '08',
],
[
'Timestamp' => '2022-02-21 03:00',
'Date' => '2022-02-21',
'Hour' => '03',
],
[
'Timestamp' => '2022-02-21 00:00',
'Date' => '2022-02-21',
'Hour' => '00',
],
];
$Timestamp = array_column($tempData, 'Timestamp');
array_multisort($Timestamp, SORT_DESC, $tempData);
print_r($tempData);
Output:
Array
(
[0] => Array
(
[Timestamp] => 2022-02-21 08:00
[Date] => 2022-02-21
[Hour] => 08
)
[1] => Array
(
[Timestamp] => 2022-02-21 06:00
[Date] => 2022-02-21
[Hour] => 06
)
[2] => Array
(
[Timestamp] => 2022-02-21 03:00
[Date] => 2022-02-21
[Hour] => 03
)
[3] => Array
(
[Timestamp] => 2022-02-21 00:00
[Date] => 2022-02-21
[Hour] => 00
)
)
This question already has answers here:
Is there a function to extract a 'column' from an array in PHP?
(15 answers)
Closed 6 years ago.
I am trying to get values for each field eg. translation in subarrays without foreach. Is it possible?
Array
(
[0] => Array
(
[group_id] => 11
[group_translation] => Extras
[id] => 21
[operation] => +
[price] => 5
[price_by] => once
[price_type] => fixed
[translation] => Pick up
[price_total] => 5
)
[1] => Array
(
[group_id] => 11
[group_translation] => Extras
[id] => 22
[operation] => +
[price] => 10
[price_by] => once
[price_type] => fixed
[translation] => Drinks
[price_total] => 10
)
)
Thank you!
Sure that is possible:
<?php
$data = [
[
'group_id' => 11,
'group_translation' => 'Extras',
'id' => 21,
'operation' => '+',
'price' => 5,
'price_by' => 'once',
'price_type' => 'fixed',
'translation' => 'Pick up',
'price_total]' => 5
],
[
'group_id' => 11,
'group_translation' => 'Extras',
'id' => 22,
'operation' => '+',
'price' => 10,
'price_by' => 'once',
'price_type' => 'fixed',
'translation' => 'Drinks',
'price_total' => 10
]
];
$extract = [];
array_walk($data, function($element) use (&$extract) {
$extract[] = $element['translation'];
});
var_dump($extract);
The output obviously is:
array(2) {
[0] =>
string(7) "Pick up"
[1] =>
string(6) "Drinks"
}
Can you sum the below array of sales by weeknumber
Array
(
[0] => Array
(
[DATE] => 2015-03-06
[store] => 18
[weeknum] => 11
[sales] => 10
)
[1] => Array
(
[DATE] => 2015-03-08
[store] => 18
[weeknum] => 11
[sales] => 5
)
[2] => Array
(
[DATE] => 2015-03-09
[store] => 18
[weeknum] => 11
[sales] => 5
)
I would like to achieve something like this
[0] => Array
(
[store] => 18
[weeknum] => 11
[sales] => 20
)
so far i have tried array sum but that doesnt seem to work
There are many different ways and answers (eg.).
For instance:
Using Array Reduce:
$total_sales = array_reduce($items, function($carry, $item){
$carry['store'] = $item['store'];
$carry['weeknum'] = $item['weeknum'];
$carry['sales'] += $item['sales'];
return $carry;
}, []);
Or Using Array column:
$total_sales = array_sum(array_column($items, 'sales'));
Simply iterate through the array and add the field values to a sum container.
I've also added the store number as a unique identifier in case there's multiple stores you want individual info for. If you want it for all stores just change $key = $weekNumber . $item['store']; out with $key = $weekNumber;.
Data:
$items = [
[
'DATE' => '2015-03-06',
'store' => 18,
'weeknum' => 11,
'sales' => 10,
],
[
'DATE' => '2015-03-08',
'store' => 18,
'weeknum' => 11,
'sales' => 5,
],
[
'DATE' => '2015-03-09',
'store' => 18,
'weeknum' => 11,
'sales' => 5,
],
[
'DATE' => '2015-03-09',
'store' => 18,
'weeknum' => 12,
'sales' => 5,
],
];
Code:
<?php
$storeWeekSums = [];
foreach ($items as $item) {
// Save the key to refer to it later
$weekNumber = $item['weeknum'];
$key = $weekNumber . $item['store'];
if (!isset($weekSums[$weekNumber])) {
// The week and store does not already exist, let's create it with a value
$storeWeekSums[$key] = [
'store' => $item['store'],
'weeknum' => $item['weeknum'],
'sales' => $item['sales'],
];
} else {
// The week and store already exists, so we'll add to the current value instead
$storeWeekSums[$key]['sales'] += $item['sales'];
}
}
print_r($storeWeekSums);
Output::
Array
(
[1118] => Array
(
[store] => 18
[weeknum] => 11
[sales] => 5
)
[1218] => Array
(
[store] => 18
[weeknum] => 12
[sales] => 5
)
)
DEMO
I'm trying to group the data in an array of associative arrays by three columns (year, month, grupo) and sum another column (quantity).
Given an array like:
$in = [
['year' => '2010', 'month' => '11', 'grupo' => '2', 'quantity' => 3],
['year' => '2010', 'month' => '11', 'grupo' => '3', 'quantity' => 4],
['year' => '2011', 'month' => '2', 'grupo' => '2', 'quantity' => 4],
['year' => '2011', 'month' => '2', 'grupo' => '2', 'quantity' => 4],
['year' => '2012', 'month' => '3', 'grupo' => '4', 'quantity' => 3]
['year' => '2012', 'month' => '3', 'grupo' => '4', 'quantity' => 3]
];
I want get:
[
['year' => '2010', 'month' => '11', 'grupo' => '2', 'quantity' => 3],
['year' => '2010', 'month' => '11', 'grupo' => '3', 'quantity' => 4],
['year' => '2011', 'month' => '2', 'grupo' => '2', 'quantity' => 8],
['year' => '2012', 'month' => '3', 'grupo' => '4', 'quantity' => 6]
]
I've tried something like this:
$out = array();
foreach ($in as $row) {
if (!isset($out[$row['year']['month']['grupo']])) {
$out[$row['year']['month']['grupo']] = array(
'year' => $row['year'],
'month' => $row['month'],
'grupo' => $row['grupo'],
'quantity' => 0,
);
}
$out[$row['year']['month']['grupo']]['quantity'] += $row['quantity'];
}
$out = array_values($out);
but it fails while trying to group the 3 fields.
I think the earlier answers overlooked the desired result -- the solutions from #hellcode and #Rasclatt create unnecessarily deep structures.
The coding attempt in the question was very close to being right, there was only a flaw in generating unique grouping keys in the first level.
To generate unique grouping keys, you must forge a string from the multiple identifying values in the row. In other words, "compose" a unique value from the three targeted column values -- a composite key.
Code: (Demo)
$result = [];
foreach ($in as $row) {
$compositeKey = implode(array_slice($row, 0, 3));
if (!isset($result[$compositeKey])) {
$result[$compositeKey] = $row;
} else {
$result[$compositeKey]['quantity'] += $row['quantity'];
}
}
var_export(
array_values($result)
);
Try this:
$out = array();
foreach ($in as $row) {
if(! isset($out[$row['year']][$row['month']][$row['grupo']])) {
$out[$row['year']][$row['month']][$row['grupo']]=0;
}
$out[$row['year']][$row['month']][$row['grupo']] += $row['quantity'];
}
print_r($out);
It will output your desired values, but as a multidimensional value array, not as a flat array with key => value pairs:
Array
(
[2010] => Array
(
[11] => Array
(
[2] => 3
[3] => 4
)
)
[2011] => Array
(
[2] => Array
(
[2] => 8
)
)
[2012] => Array
(
[3] => Array
(
[4] => 6
)
)
)
But you can rearrange your array:
$out2 = array();
foreach($out as $year => $year_array) {
foreach($year_array as $month => $month_array) {
foreach($month_array as $grupo => $quantity) {
$out2[] = array('year' => $year, 'month' => $month, 'grupo' => $grupo, 'quantity' => $quantity);
}
}
}
print_r($out2);
This will output:
Array
(
[0] => Array
(
[year] => 2010
[month] => 11
[grupo] => 2
[quantity] => 3
)
[1] => Array
(
[year] => 2010
[month] => 11
[grupo] => 3
[quantity] => 4
)
[2] => Array
(
[year] => 2011
[month] => 2
[grupo] => 2
[quantity] => 8
)
[3] => Array
(
[year] => 2012
[month] => 3
[grupo] => 4
[quantity] => 6
)
)
This will retain values and also give sum.
foreach($in as $row) {
$out[$row['year']][$row['month']][$row['grupo']]['quantity'][] = $row['quantity'];
$out[$row['year']][$row['month']][$row['grupo']]['sum'] = array_sum($out[$row['year']][$row['month']][$row['grupo']]['quantity']);
}
print_r($out);
GIVES
Array
(
[2010] => Array
(
[11] => Array
(
[2] => Array
(
[quantity] => Array
(
[0] => 3
)
[sum] => 3
)
[3] => Array
(
[quantity] => Array
(
[0] => 4
)
[sum] => 4
)
)
)
[2011] => Array
(
[2] => Array
(
[2] => Array
(
[quantity] => Array
(
[0] => 4
[1] => 4
)
[sum] => 8
)
)
)
[2012] => Array
(
[3] => Array
(
[4] => Array
(
[quantity] => Array
(
[0] => 3
[1] => 3
)
[sum] => 6
)
)
)
)