Counting values within multidimensional arrays? - php

I have a large array where I basically need to count the number of uniques:
example array
The end result I am looking for something like
$result = array(
'A3D5' => array('P2' => 1, 'P3' => 1, 'P4' => 1, 'total' => 3),
'AE5S' => array('P4' => 1, 'total' => 1)
);
I've tried foreaching through but can't seem to figure out how to sort them into another key, something like $zone = "P{$array['zone']}"; $result[$zone][$prestige]++ or seems to kind of not work or just error.

$array = array(
"denizen" => array
(
"prestige" => 2,
"zone" => "A3D5",
"scope_frag" => 765
),
"생각" => array
(
"prestige" => 4,
"zone" => "A3D5",
"scope_frag" => 135
),
"Ryans" => array
(
"prestige" => 3,
"zone" => "A3D5",
"scope_frag" => 78
),
"지적인" => array
(
"prestige" => 2,
"zone" => "AE5S",
"scope_frag" => 481
)
);
foreach ($array as $group) {
$zones[$group["zone"]][] = $group["prestige"];
}
foreach ($zones as $name => $zone) {
$total = count($zone);
foreach ($zone as $prestige) {
$result[$name]["P".$prestige] += 1;
}
ksort($result[$name]);
$result[$name]["total"] = $total;
}
echo "<pre>";
print_r($result);
echo "</pre>";

Related

How to change date format in multidimensional array and iterate all array with key

I have a multidimensional array with key and value and some key is empty also. Then I want to set a value for internal not empty array.
$oldArray = array("Lexus LS600" => array(),
"Toyota Alphard" => array(),
"Benz S550" => array(0 => array(
"card_no" => "G2FPCBS3",
"travel_date" => "2020-09-10"
"travel_time" => "16:15:00",
"car_id" => 12,
"return_time" => "17:25")),
"BMW X6" => array());
I had this array but I want to set return_time 00:00 all over array. I tried foreach loop but foreach is remove empty array but I want empty array also.
I want this type array:-
$newArray = array("Lexus LS600" => array(),
"Toyota Alphard" => array(),
"Benz S550" => array(0 => array(
"card_no" => "G2FPCBS3",
"travel_date" => "2020-09-10"
"travel_time" => "16:15:00",
"car_id" => 12,
"return_time" => "00:00")),
"BMW X6" => array());
Try this foreach again, I think it will solve your problem if I understood you correctly.
foreach ($arrays as $key => $values) {
if (is_array($values)) {
if (count($values)) {
foreach ($values as $index => $data) {
$arrays[$key][$index]['return_time'] = "00:00";
}
} else {
$arrays[$key] = $values;
}
}
}
It will change return_time to "00:00" and also retain the empty index to your array.
array_walk_recursive() is very suitable for this.
$oldArray = array("Lexus LS600" => array(),
"Toyota Alphard" => array(),
"Benz S550" => array(0 => array(
"card_no" => "G2FPCBS3",
"travel_date" => "2020-09-10",
"travel_time" => "16:15:00",
"car_id" => 12,
"return_time" => "17:25")),
"BMW X6" => array());
$keySearch = "return_time";
$replaceWith = "00:00";
array_walk_recursive(
$oldArray,
function(&$val,$key) use($keySearch,$replaceWith){
if($key == $keySearch) $val = $replaceWith;
}
);
var_export($oldArray);
Output:
array (
'Lexus LS600' =>
array (
),
'Toyota Alphard' =>
array (
),
'Benz S550' =>
array (
0 =>
array (
'card_no' => 'G2FPCBS3',
'travel_date' => '2020-09-10',
'travel_time' => '16:15:00',
'car_id' => 12,
'return_time' => '00:00',
),
),
'BMW X6' =>
array (
),
)
Use two foreach loops to traverse the limited-depth array and make all values modifiable by reference (& before the variable). In doing so, you don't need to create a separate array, just update the input array. It is SUPER easy to read and maintain.
Code: (Demo)
foreach ($array as &$cars) {
foreach ($cars as &$entry) {
if ($entry) {
$entry["return_time"] = "00:00";
}
}
}
var_export($array);
Output:
array (
'Lexus LS600' =>
array (
),
'Toyota Alphard' =>
array (
),
'Benz S550' =>
array (
0 =>
array (
'card_no' => 'G2FPCBS3',
'travel_date' => '2020-09-10',
'travel_time' => '16:15:00',
'car_id' => 12,
'return_time' => '00:00',
),
),
'BMW X6' =>
array (
),
)

How to subtract all column values in multi-dimensional array in Php?

How can I subtract all the columns values? My array is like
Array
(
[0] => Array
(
[id] => 1
[web_traffic] => 442
[form_users] => 131
[date] => 20181004
)
[1] => Array
(
[id] => 2
[web_traffic] => 102
[form_users] => 15
[date] => 20181003
)
[2] => Array
(
[id] => 3
[web_traffic] => 387
[form_users] => 97
[date] => 20181002
)
)
I need to subtract the each column(except date & id) and get the result based on date(Ascending order). For example 20181004 means 4th October 2018. My output should like the below
Array
(
[web_traffic] => -152
[form_users] => -49
)
My code took reference from How to sum all column values in multi-dimensional array?
foreach ($data as $value) {
unset($value[ 'id' ]);
$time = date('Ymd', strtotime($value[ 'date' ]));
if (in_array($time, $dates)) {
$value[ 'date' ] = $time;
foreach ($value as $key => $secondValue) {
if ( !isset($output[ $key ])) {
$output[ $key ] = 0;
}
$output[ $key ] -= $secondValue;
}
}
}
Use PHP array_reduce() and array_column() like this:
$initial_array = array(array('id' => 1,
'web_traffic' => 442,
'form_users' => 131,
'date' => 20181004),
array('id' => 2,
'web_traffic' => 102,
'form_users' => 15,
'date' => 20181003),
array('id' => 3,
'web_traffic' => 387,
'form_users' => 97,
'date' => 20181002));
function sum($carry, $item)
{
$carry -= $item;
return $carry;
}
$web_traffic = array_column($initial_array, "web_traffic");
$form_users = array_column($initial_array, "form_users");
$date = array_column($initial_array, "date");
array_multisort($date, SORT_ASC, $form_users, SORT_DESC, $initial_array);
$result_array = Array(
"web_traffic" => array_reduce(array_column($initial_array, "web_traffic"), "sum",2*$initial_array[0]['web_traffic']),
"form_users" => array_reduce(array_column($initial_array, "form_users"), "sum",2*$initial_array[0]['form_users'])
);
print_r($result_array);
I would first sort the array using usort() in example.
Sorting first, because that can be tricky to substract in 1 loop the oldest datas to the newers one.
Separating intentions provide a cleaner code, easier to maintain.
The dates don't need to be converted into a date. The string is well formatted and can be used as is in a comparison and a sort. "20170101" < "20180101", "20180101" < "20181001" and "20181002" < "20181004"
When done, I'll save the first values as initial values to be used in substract.
Then, loop the sorted array and substract the 'web_traffic' and 'form_users' to the initial values.
$datas = array(array('id' => 1,
'web_traffic' => 442,
'form_users' => 131,
'date' => 20181004),
array('id' => 2,
'web_traffic' => 102,
'form_users' => 15,
'date' => 20181003),
array('id' => 3,
'web_traffic' => 387,
'form_users' => 97,
'date' => 20181002));
//If needed, you can backup the original array, because usort() will modify it.
$backUpDatas = $datas;
//Sort
usort($datas, function ($arr1, $arr2)
{
if (isset($arr1['date']) && isset($arr2['date']))
{
if ($arr1['date'] == $arr2['date'])
return (0);
return (($arr1['id'] > $arr2['id']) ? (-1) : (1));
}
});
//Initial values
$finalValues['web_traffic'] = $datas[0]['web_traffic'];
$finalValues['form_users'] = $datas[0]['form_users'];
//Substract
foreach ($datas as $key => $value)
{
if ($key > 0)
{
if (isset($value['web_traffic']))
$finalValues['web_traffic'] -= $value['web_traffic'];
if (isset($value['form_users']))
$finalValues['form_users'] -= $value['form_users'];
}
}
var_dump($finalValues);
Output :
array (size=2)
'web_traffic' => int -157
'form_users' => int -49

Merge Array Issue

I have several arrays that all have this structure:
array (
526744 =>
array (
'completed' => 13,
'total' => 24,
'topics' =>
array (
),
'lessons' =>
array (
526745 => 1,
526747 => 1,
526749 => 1,
526751 => 0,
526757 => 0,
526759 => 0,
526761 => 1,
526763 => 0,
526765 => 0,
526767 => 1,
),
'last_id' => 526793,
),
526818 =>
array (
'completed' => 0,
'total' => 22,
'topics' =>
array (
),
'lessons' =>
array (
526819 => 0,
526821 => 1,
526823 => 1,
526845 => 0,
526847 => 1,
526849 => 1,
526859 => 1,
526861 => 1,
),
'last_id' => 526861,
),
)
The number in the outer-most element of the array is a course id. The list of numbers in the inner-most array elements are lesson ids.
I want to merge all of the arrays that contain this structure together. But only ones with the course id of 526744.
If I do something like this:
foreach($results2 as $result2) {
$new_array = unserialize($result2->course_progress);
$final_array = array_merge($final_array, $new_array);
$backup_array = $new_array;
}
This works fine, but it merges the entire arrays, including all courses.
However if I specify the course_id like this:
foreach($results2 as $result2) {
$new_array = unserialize($result2->course_progress);
$newarray = $new_array[526744];
$final_array = array_merge($final_array, $new_array);
$backup_array = $new_array;
}
It no longer merges at all and just lists out the last array for that 1 single course specified.
Any ideas on what is causing this and how to fix it?
Thanks
I have check your code and found the issue, you have used $new_array[526744] which is wrong. it should be array($new_array[526744])
Check this code:
foreach($results2 as $result2) {
$new_array = unserialize($result2->course_progress);
$newarray = array($new_array[526744]);
$final_array = array_merge($final_array, $new_array);
$backup_array = $new_array;
}

how to convert multi array to json multi array

i have foreach loop that returns multi-array from the database
and i want to convert this array to multi array in json ,
how to do this ?
php array example
Array
(
[0] => Array
(
[it_code] => 2894
[it_quantity] => 300
[it_price] => 0
[it_notes] =>
)
[1] => Array
(
[it_code] => 2894
[it_quantity] => 284
[it_price] => 0
[it_notes] =>
)
[2] => Array
(
[it_code] => 2894
[it_quantity] => 4
[it_price] => 0
[it_notes] =>
)
[3] => Array
(
[it_code] => 2894
[it_quantity] => 3
[it_price] => 0
[it_notes] =>
)
)
i want returned json to be like this format
[
['2894', 300, 0,''],
['2894', 284, 0,''],
['2894', 4, 0,''],
['2894', 3, 0,''],
['2894', 10, 0, '']
]
my code like this
$this->db->where("it_parent_item", $parent_id);
$this->db->select("d_items.it_code,d_items_type.it_ty_ar_desc,d_items.it_quantity,d_items.it_price,it_notes");
$this->db->join('d_items_type','d_items_type.it_ty_id=d_items.it_type','left');
$this->db->from("d_items");
$result = $this->db->get()->result_array();
echo "<pre>";
print_r($result);
echo "</pre>";
You can use array_values() and array_walk_recursive() to convert integer to string
$newArray = array();
foreach($sourceArray as $element) {
$newArray[] = array_values($element);
}
array_walk_recursive($newArray,
function(&$value, $key){
$value = (string)$value;
});
print_r (json_encode($newArray));
Note that other answers will give null instead of ''.
So, without using array_values, this code returns all values, but in case there is any null, it returns '' instead (as expected in the question):
$arr = array();
foreach($foo as $value){
$tmp = array();
foreach($value as $v){
$tmp[] = $v===null ? '' : $v;
}
$arr[] = $tmp;
}
echo json_encode($arr);
Output:
[[2894,300,0,""],[2894,284,0,""],[2894,4,0,""],[2894,3,0,""]]
[
[2894,300,0,""],
[2894,284,0,""],
[2894,4,0,""],
[2894,3,0,""]
]
This a copyable array:
$foo = array
(
0 => array
(
'it_code' => 2894,
'it_quantity' => 300,
'it_price' => 0,
'it_notes' => null
),
1 => Array
(
'it_code' => 2894,
'it_quantity' => 284,
'it_price' => 0,
'it_notes' => null
),
2 => Array
(
'it_code' => 2894,
'it_quantity' => 4,
'it_price' => 0,
'it_notes' => null
),
3 => Array
(
'it_code' => 2894,
'it_quantity' => 3,
'it_price' => 0,
'it_notes' => null
),
);
Here's the initial array (shown like a PHP array, but the same as your post):
$initialArray = array(
array(
"it_code" => 2894,
"it_quantity" => 300,
"it_price" => 0,
"it_notes" => '',
),
array(
"it_code" => 2894,
"it_quantity" => 284,
"it_price" => 0,
"it_notes" => '',
),
array(
"it_code" => 2894,
"it_quantity" => 4,
"it_price" => 0,
"it_notes" => '',
),
array(
"it_code" => 2894,
"it_quantity" => 3,
"it_price" => 0,
"it_notes" => '',
),
);
You can loop over each element, assigning just the values to a new set of arrays, like this:
$newArray = array();
foreach ($initialArray as $subArray)
{
$newArray[] = array_values($subArray);
}
The resulting array will look like this:
[[2894,300,0,""],[2894,284,0,""],[2894,4,0,""],[2894,3,0,""]]
Looks to me like you want to loop through your array so it's formatted how you want in PHP and then convert that PHP array into JSON:
$dataArray = array(); //The array containing your values
$jsonArray = array(); //The array which will be formatted for json
foreach($dataArray as $value){
$keylessValues = array_values($value);
$jsonArray[] = $keylessValues;
}
$jsonArray = json_encode($jsonArray); //This is now a JSON array storing your values
What we do here is move through the array and then take only the values with array_values() and put them into a new index in our $jsonArray.
Once we have moved through the entire array we can convert our newly formatted and populated array into JSON with json_encode()
It's worth noting that your values that are set as '' will come through as null. If you need those values as '' instead of null have a look at the answer #FirstOne gave.

need soting multi dimensional array based on another array displaying order

I need sorting array based another array sort value.
Actual array : array(name=>'JK',age=>'20',place=>'India',year=>array(marks1=>array(sub1=>50,sub3=>70,sub7=>65,sub5=>75,sub4=>35), marks2=>array(sub8=>50,sub10=>70,sub12=>75,sub9=>35,sub11=>65))
sorting order array : array(name=>1,year=>2,age=>3,place=>4,sub1=>5,sub3=>6,sub4=>7,sub5=>8,sub7=>9,sub8=>10,sub9=>11,sub10=>12,sub11=>13,sub12=>14)
expected result array:
array(
name=>'JK',
year=>array(
marks1=>array(
sub1=>50,
sub3=>70,
sub4=>35,
sub5=>75
sub7=>65
),
marks2=>array(
sub8=>50,
sub9=>35,
sub10=>70,
sub11=>65,
sub12=>75
),
age=>'20',
place=>'India'
)
I hope this will help :)
$array1 = array(name=>'JK',age=>'20',place=>'India',year=>array(marks1=>array(sub1=>50,sub3=>70,sub7=>65,sub5=>75,sub4=>35), marks2=>array(sub8=>50,sub10=>70,sub12=>75,sub9=>35,sub11=>65));
$array2 = array(name=>1,year=>2,age=>3,place=>4,sub1=>5,sub3=>6,sub4=>7,sub5=>8,sub7=>9,sub8=>10,sub9=>11,sub10=>12,sub11=>13,sub12=>14);
//final array
$final_array = array();
//for each value in sorting array
foreach ($array2 as $key => $value)
{
//store result in final array
$final_array[$value] = $array1[$key];
}
//display array for check result
var_dump($final_array);
I am not exactly sure what is being asked. However, I will take a shot. I think the function you are looking for is uksort.
<?php
$array1 = array(name=>'JK',age=>'20',place=>'India',year=>array(marks1=>array(sub1=>50,sub3=>70,sub7=>65,sub5=>75,sub4=>35), marks2=>array(sub8=>50,sub10=>70,sub12=>75,sub9=>35,sub11=>65)));
function sorter($a,$b)
{
$array2 = array(name=>1,year=>2,age=>3,place=>4,sub1=>5,sub3=>6,sub4=>7,sub5=>8,sub7=>9,sub8=>10,sub9=>11,sub10=>12,sub11=>13,sub12=>14);
return $array2[$a] > $array2[$b];
}
uksort($array1, "sorter");
var_dump($array1);
?>
Here is an example of it running on codepad. You will probably have to work out a bit more since the subs are not sorted. But, possibly is_array can help you out.
$arr1 = array(
'name' => 'JK',
'age' => 20,
'place' => 'India',
'year' =>
array(
'marks1' =>
array('sub1' => 50,
'sub3' => 70,
'sub7' => 65,
'sub5' => 75,
'sub4' => 35),
'marks2' =>
array('sub8' => 50,
'sub10' => 70,
'sub12' => 75,
'sub9' => 35,
'sub11' => 65)));
$arr2 = array('name' => 1, 'year' => 2, 'age' => 3, 'place' => 4, 'sub1' => 5, 'sub3' => 6, 'sub4' => 7, 'sub5' => 8, 'sub7' => 9, 'sub8' => 10, 'sub9' => 11, 'sub10' => 12, 'sub11' => 13, 'sub12' => 14);
foreach ($arr1['year'] as $key => &$value){
uksort($value, function ($a, $b) use($arr2){
return $arr2[$a] - $arr2[$b];
});
}
uksort($arr1, function ($a, $b) use($arr2){
return $arr2[$a] - $arr2[$b];
});
print_r($arr1);
Output:
Array
(
[name] => JK
[year] => Array
(
[marks1] => Array
(
[sub1] => 50
[sub3] => 70
[sub4] => 35
[sub5] => 75
[sub7] => 65
)
[marks2] => Array
(
[sub8] => 50
[sub9] => 35
[sub10] => 70
[sub11] => 65
[sub12] => 75
)
)
[age] => 20
[place] => India
)

Categories