How many times an element shows in a multidimensional array - php

I need to know how many times a "phase" shows up, and if it's completed or not.
The final objective is to show:
Phase 1: 50% completed
Phase 2: 0% completed
Tasks:
Array
(
[0] => Array
(
[phase] => 1
[tasks_status] => completed
)
[1] => Array
(
[phase] => 1
[tasks_status] => pending
)
[2] => Array
(
[phase] => 2
[tasks_status] => pending
)
)
Phases:
Array
(
[0] => Array
(
[title] => Briefing e Planejamento
[id] => 1
[created] => 1437436800
)
[1] => Array
(
[title] => Rabiscos e Design
[id] => 2
[created] => 1438128000
)
)
edit
So, with the help of you guys who answered, I've managed to do it! Here's the result:
/** Define wich tasks has been completed **/
foreach ($tasks as $task) {
if ($task['status'] == "completed") {
foreach ($fases as &$fase) {
if ($fase['id'] == $task['fase_id']) {
$fase['numero_total_fases']++;
$fase['completed']++;
}
}
} elseif ($task['status'] == "pending") {
foreach ($fases as &$fase) {
if ($fase['id'] == $task['fase_id']) {
$fase['numero_total_fases']++;
$fase['pending']++;
}
}
} elseif ($task['status'] == "behind schedule") {
foreach ($fases as &$fase) {
if ($fase['id'] == $task['fase_id']) {
$fase['numero_total_fases']++;
$fase['behind schedule']++;
}
}
}
unset($fase);
}
/** Define progress percentage **/
foreach ($fases as &$fase) {
$fase['progresso'] = round(($fase['completed'] / ($fase['numero_total_fases'])) * 100);
}
/** Print phases progress **/
$f = 1;
foreach ($fases as $fase) {
echo 'Fase '.$f.' - '.$fase['title'].' = '.$fase['progresso'].'% completed';
}

A little slow to the draw, but since I already wrote it, here's my answer too. It's always helpful to see that most programming tasks can be done several ways:
<?php
$tasks = array(
array(
'phase' => 1,
'tasks_status' => 'completed'
),
array(
'phase' => 1,
'tasks_status' => 'pending'
),
array(
'phase' => 2,
'tasks_status' => 'pending'
)
);
//$phases = array();
$phases = array(
1=>array(
'title'=>'Briefing e Planejamento',
'id'=>1,
'created'=>1437436800
),
2=>array(
'title'=>'Rabiscos e Design',
'id'=>2,
'created'=>1438128000
)
);
foreach($tasks as $key=>$task){
if(isset($phases[$task['phase']])){
$thisPhase = $phases[$task['phase']];
}
else{
$thisPhase = array(
'completed' => 0,
'pending' => 0
);
}
$thisPhase[$task['tasks_status']]++;
$phases[$task['phase']] = $thisPhase;
}
foreach($phases as $name=>$phase){
echo $phase['title'].": ".round(($phase['completed'] / ($phase['completed'] + $phase['pending'])) * 100)."% completed <br>";
}
?>
I know you've already finished, but regarding the phases array - you should have put that in the original question if you wanted it worked into the answer. My suggestion, however, would be to use the ID of the phase as the index name in your phases array. The solution I posted will work with that too - and you can then use $phase in the final foreach loop to show the title or created time.

Is this what you are after?
I assume you want to calculate the percentage based on your original array.
<?php
$tasks = array(
array(
'phase' => 1,
'tasks_status' => 'completed'
),
array(
'phase' => 1,
'tasks_status' => 'pending'
),
array(
'phase' => 2,
'tasks_status' => 'pending'
),
);
$phases_arr = array();
foreach($tasks as $task) {
if(!array_key_exists($task['phase'], $phases_arr)) {
$phases_arr[$task['phase']] = array();
}
$phases_arr[$task['phase']][] = $task;
}
$phases = array();
foreach($phases_arr as $phase_num => $phase) {
$p = array(
'phase' => $phase_num,
'total' => count($phase),
'complete' => 0,
'percent' => 0
);
foreach($phase as $task) {
if($task['complete']) $p['complete']++;
}
$p['percent'] = ($p['complete'] / $p['total']) * 100;
$phases[$phase_num] = $p;
}
foreach($phases as $phase) {
echo "<p>Phase {$phase['phase']}: {$phase['percent']}% completed</p>";
}

Your inputs,
$tasks = array( array('phase' => 1, 'tasks_status' => 'completed'),
array('phase' => 1, 'tasks_status' => 'pending'),
array('phase' => 2, 'tasks_status' => 'pending'),
);
Consider this,
$phase = array();
foreach ($tasks as $key => $value)
{
$phase[$value['phase']][] = $value['tasks_status'] == 'completed' ? 50 : 0 ;
}
function get_phase_percentage($i)
{
global $phase;
if(isset($phase[$i]) && is_array($phase[$i]))
return array_sum($phase[$i]);
return 0;
}
Use it like,
Phase 1: <?php echo get_phase_percentage(1)?>% completed
Phase 2: <?php echo get_phase_percentage(2)?>% completed

Related

PHP – Group output with same ID from within foreach loop

I have a user upload a .csv file from the backend of Wordpress through a custom file upload field (Advanced custom fields). I then call this field to retrieve the data from that file to create an array of said data:
$upload_cq = get_field('report_current_quarter');
$report_cq = array();
if(($handle_cq = fopen($upload_cq, "r")) !== FALSE)
{
while(($data_cq = fgetcsv($handle_cq, 1000, ",")) !== FALSE)
{
$report_cq[] = $data_cq;
}
$results_cq = array_slice($report_cq, 3); // remove unwanted row
fclose($handle_cq);
}
Once I create the array, I then create another array with a key and associate value, and ensure that the "team_id" column is present & not empty, as so (there is a teamName function which I won't get into):
foreach($results_cq as $results)
{
$team_id = $results[6];
if(!empty($team_id))
{
$team_totals_cq[] = array(
'id' => $team_id,
'team' => teamName($team_id),
'total_volume' => $results[41],
'total_closed' => $results[24],
'listings_closed' => $results[22],
'buyers_closed' => $results[23],
'total_agc' => $results[29],
'rental_agc' => $results[30],
);
}
}
echo '<pre>'; print_r($team_totals_cq); echo '</pre>';
When printing the array, I get the following. My question now is; How do I group results with the same team "id" and add up their results (results = total_volume, total_closed, listings_closed, buyers_closed, total_agc, and rental_agc):
Array
(
...
[6] => Array
(
[id] => 0011
[team] => Williamson Team
[total_volume] => $990,000
[total_closed] => 4
[listings_closed] => $0.00
[buyers_closed] => 1
[total_agc] => $20,812.50
[rental_agc] => $23,812.50
)
...
[9] => Array
(
[id] => 0011
[team] => Williamson Team
[total_volume] => $415,000
[total_closed] => 2
[listings_closed] => $0.00
[buyers_closed] => 0
[total_agc] => $12,450.00
[rental_agc] => $12,450.00
)
...
)
I have tried everything within my abilities, and nothing has worked.
One method is to use team_id as keys in $team_totals_cq then simply add up the values as you go through the loop.
(Note: The preg_replace function strips anything that aren't numbers or .)
$team_totals_cq = [];
foreach ($results_cq as $results) {
$team_id = $results[6];
if (!empty($team_id)) {
if (!isset($team_totals_cq[$team_id])) {
$team_totals_cq[$team_id] = [
'id' => $team_id,
'team' => teamName($team_id),
'total_volume' => preg_replace("/[^0-9\.]/", '', $results[41]),
'total_closed' => $results[24],
'listings_closed' => preg_replace("/[^0-9\.]/", '', $results[22]),
'buyers_closed' => $results[23],
'total_agc' => preg_replace("/[^0-9\.]/", '', $results[29]),
'rental_agc' => preg_replace("/[^0-9\.]/", '', $results[30])
];
} else {
$team_totals_cq[$team_id]['total_volume'] += preg_replace("/[^0-9\.]/", '', $results[41]);
$team_totals_cq[$team_id]['total_closed'] += $results[24];
$team_totals_cq[$team_id]['listings_closed'] += preg_replace("/[^0-9\.]/", '', $results[22]);
$team_totals_cq[$team_id]['buyers_closed'] += $result[23];
$team_totals_cq[$team_id]['total_agc'] += preg_replace("/[^0-9\.]/", '', $results[29]);
$team_totals_cq[$team_id]['rental_agc'] += preg_replace("/[^0-9\.]/", '', $results[30]);
}
}
}

JSON php extract data (where a statement is true)

I'm trying to catch specific data from a weather forecast API request (JSON output). The request gives me data for the next 3 days but I only need the next day. Here a snippet of the output:
array (
'cod' => '200',
'message' => 0.00259999999999999988065102485279567190445959568023681640625,
'cnt' => 40,
'list' =>
array (
0 =>
array (
'dt' => 1526461200,
'main' =>
array (
'temp' => 292.93000000000000682121026329696178436279296875,
'temp_min' => 292.05000000000001136868377216160297393798828125,
'temp_max' => 292.93000000000000682121026329696178436279296875,
'pressure' => 1019.259999999999990905052982270717620849609375,
'sea_level' => 1029.170000000000072759576141834259033203125,
'grnd_level' => 1019.259999999999990905052982270717620849609375,
'humidity' => 71,
'temp_kf' => 0.88000000000000000444089209850062616169452667236328125,
),
'weather' =>
array (
0 =>
array (
'id' => 802,
'main' => 'Clouds',
'description' => 'scattered clouds',
'icon' => '03d',
),
),
'clouds' =>
array (
'all' => 36,
),
'wind' =>
array (
'speed' => 4.20000000000000017763568394002504646778106689453125,
'deg' => 37.00240000000000151203494169749319553375244140625,
),
'sys' =>
array (
'pod' => 'd',
),
'dt_txt' => '2018-05-16 09:00:00',
),
1 =>
array (
'dt' => 1526472000,
'main' =>
array (
'temp' => 293.6100000000000136424205265939235687255859375,
'temp_min' => 292.95800000000002683009370230138301849365234375,
'temp_max' => 293.6100000000000136424205265939235687255859375,
'pressure' => 1019.799999999999954525264911353588104248046875,
'sea_level' => 1029.65000000000009094947017729282379150390625,
'grnd_level' => 1019.799999999999954525264911353588104248046875,
'humidity' => 66,
'temp_kf' => 0.66000000000000003108624468950438313186168670654296875,
),
'weather' =>
array (
0 =>
array (
'id' => 803,
'main' => 'Clouds',
'description' => 'broken clouds',
'icon' => '04d',
),
),
'clouds' =>
array (
'all' => 56,
),
'wind' =>
array (
'speed' => 5.79999999999999982236431605997495353221893310546875,
'deg' => 38.0009000000000014551915228366851806640625,
),
'sys' =>
array (
'pod' => 'd',
),
'dt_txt' => '2018-05-16 12:00:00',
)
I'm trying to get the 'all' values where 'dt_txt' starts from 0am the next day to 0pam the day after.
For now I'm using the following php code without checking for dt_txt:
<?php
$url = "http://api.openweathermap.org/data/2.5/forecast?q=D%C3%BClmen,de&mode=json";
$response = file_get_contents($url);
$obj = json_decode($response);
$t = 0;
$regen = 0;
$regendiv = 0;
for($i=0; $i < 10; $i++) {
$fg = $obj->list[$i]->clouds->all;
$regen += $fg;
}
echo $regen;
?>
My code requires me to run the request at a specific time (like close to midnight) in order to catch the 'all' values for the next day. Is there any way to check for 'dt_text' = the next day?
My Idea would be something like this:
for($i=0; $i < 10; $i++) {
$fg = $obj->list[$i]->clouds->all;
if (strpos($obj->list[$i]->dt_txt), $date){
$regen += $fg;
}
**//But how do I get $date to be the following day**
}
echo $regen;
?>
I was able to solve it this way:
<?php
$nextWeek = time() + (24 * 60 * 60);
$morgen = date('Y-m-d', $nextWeek);
$url = "http://api.openweathermap.org/data/2.5/forecast?q=D%C3%BClmen,de&mode=json";
$response = file_get_contents($url);
$obj = json_decode($response);
$quote = 0;
for($i=0; $i < 14; $i++) {
if (strpos($obj->list[$i]->dt_txt, $morgen) !== false) {
$fg = $obj->list[$i]->clouds->all;
if($fg > 80) { $t = 1; }
$regen += $fg;
$quote++;
}
}
$regendiv = $regen / $quote;
?>
Probably not the prettiest way but it gets the job done.

How to check if a value exists in a Multidimensional array

I have an Multidimensional array that takes a similar form to this array bellow.
$shop = array( array( Title => "rose",
Price => 1.25,
Number => 15
),
array( Title => "daisy",
Price => 0.75,
Number => 25,
),
array( Title => "orchid",
Price => 1.15,
Number => 7
)
);
I would like to see if a value I'm looking for is in the array, and if so, return the position of the element in the array.
Here's a function off the PHP Manual and in the comment section.. Works like a charm.
<?php
function recursive_array_search($needle,$haystack) {
foreach($haystack as $key=>$value) {
$current_key=$key;
if($needle===$value OR (is_array($value) && recursive_array_search($needle,$value) !== false)) {
return $current_key;
}
}
return false;
}
Found this function in the PHP docs: http://www.php.net/array_search
A more naive approach than the one showed by Zander, you can hold a reference to the outer key and inner key in a foreach loop and store them.
$outer = "";
$inner = "";
foreach($shop as $outer_key => $inner_array){
foreach($inner_array as $inner_key => $value) {
if($value == "rose") {
$outer = $outer_key;
$inner = $inner_key;
break 2;
}
}
}
if(!empty($outer)) echo $shop[$outer][$inner];
else echo "value not found";
You can use array_map with in_array and return the keys you want
$search = 1.25;
print_r(
array_filter(array_map(function($a){
if (in_array($search, $a)){
return $a;
}
}, $shop))
);
Will print:
Array
(
[0] => Array
(
[Title] => rose
[Price] => 1.25
[Number] => 15
)
)
php >= 5.5
$shop = array( array( 'Title' => "rose",
'Price' => 1.25,
'Number' => 15
),
array( 'Title' => "daisy",
'Price' => 0.75,
'Number' => 25,
),
array( 'Title' => "orchid",
'Price' => 1.15,
'Number' => 7
)
);
$titles = array_column($shop,'Title');
if(!empty($titles['rose']) && $titles['rose'] == 'YOUR_SEARCH_VALUE'){
//do the stuff
}

how to find a element in a nested array and get its sub array index

when searching an element in a nested array, could i get back it's 1st level nesting index.
<?php
static $cnt = 0;
$name = 'victor';
$coll = array(
'dep1' => array(
'fy' => array('john', 'johnny', 'victor'),
'sy' => array('david', 'arthur'),
'ty' => array('sam', 'joe', 'victor')
),
'dep2' => array(
'fy' => array('natalie', 'linda', 'molly'),
'sy' => array('katie', 'helen', 'sam', 'ravi', 'vipul'),
'ty' => array('sharon', 'julia', 'maddy')
)
);
function recursive_search(&$v, $k, $search_query){
global $cnt;
if($v == $search_query){
/* i want the sub array index to be returned */
}
}
?>
i.e to say, if i'am searching 'victor', i would like to have 'dep1' as the return value.
Could anyone help ??
Try:
$name = 'victor';
$coll = array(
'dep1' => array(
'fy' => array('john', 'johnny', 'victor'),
'sy' => array('david', 'arthur'),
'ty' => array('sam', 'joe', 'victor')
),
'dep2' => array(
'fy' => array('natalie', 'linda', 'molly'),
'sy' => array('katie', 'helen', 'sam', 'ravi', 'vipul'),
'ty' => array('sharon', 'julia', 'maddy')
)
);
$iter = new RecursiveIteratorIterator(new RecursiveArrayIterator($coll), RecursiveIteratorIterator::SELF_FIRST);
/* These will be used to keep a record of the
current parent element it's accessing the childs of */
$parent_index = 0;
$parent = '';
$parent_keys = array_keys($coll); //getting the first level keys like dep1,dep2
$size = sizeof($parent_keys);
$flag=0; //to check if value has been found
foreach ($iter as $k=>$val) {
//if dep1 matches, record it until it shifts to dep2
if($k === $parent_keys[$parent_index]){
$parent = $k;
//making sure the counter is not incremented
//more than the number of elements present
($parent_index<$size-1)?$parent_index++:'';
}
if ($val == $name) {
//if the value is found, set flag and break the loop
$flag = 1;
break;
}
}
($flag==0)?$parent='':''; //this means the search string could not be found
echo 'Key = '.$parent;
Demo
This works , but I don't know if you are ok with this...
<?php
$name = 'linda';
$col1=array ( 'dep1' => array ( 'fy' => array ( 0 => 'john', 1 => 'johnny', 2 => 'victor', ), 'sy' => array ( 0 => 'david', 1 => 'arthur', ), 'ty' => array ( 0 => 'sam', 1 => 'joe', 2 => 'victor', ), ), 'dep2' => array ( 'fy' => array ( 0 => 'natalie', 1 => 'linda', 2 => 'molly', ), 'sy' => array ( 0 => 'katie', 1 => 'helen', 2 => 'sam', 3 => 'ravi', 4 => 'vipul', ), 'ty' => array ( 0 => 'sharon', 1 => 'julia', 2 => 'maddy', ), ), );
foreach($col2 as $k=>$arr)
{
foreach($arr as $k1=>$arr2)
{
if(in_array($name,$arr2))
{
echo $k;
break;
}
}
}
OUTPUT :
dept2
Demo

To print the value of array.under array

I have to print the all the value of the array written value.
[subscriber] => Array
(
[name] => Subscriber
[capabilities] => Array
(
[read] => 1
[level_0] => 1
)
[default] => Array
(
[deft] => Array (
[one] => 2
[two] => 3
)
[deft_one] => Array (
[one] => t
[two] => h
)
)
)
I have to print each value under the array. So i used a recursion function. But i cant the result. Please help me in recursion function.
Sorry, I am trying till now. Actually i have to print the wp-option table value. There are many serialise array. I want to print all the value individually. I mean when i used the code written bellow i got an array.
function option_value_change () {
global $wpdb;
$myrows = $wpdb->get_results( "SELECT *
FROM `wp_options`");
$temp_url = get_option('siteurl');
$site_url = get_site_url();
foreach ($myrows as $rows){
$option = get_option($rows->option_name);
//print_r($option);
get_option_value($option);
}
}
i can get the table. But in an array. Which array have arrays. So i used an function "get_option_value($option)". as written bellow
function get_option_value($option) {
if(!is_object($option) && !is_array($option)){
echo $option;
}
else{
foreach($option as $option_value){
if(!is_array($option_value)){
echo $option_value;
}
else {
get_option_value($option_value);
}
}
}
}
bUt i cant get all the value. its give an error as
Object of class stdClass could not be converted to string.
So how can i print all the values of the array.
You can use RecursiveArrayIterator example :
$data = array(
'subscriber' => array(
'name' => 'Subscriber',
'capabilities' => array(
'read' => 1,
'level_0' => 1,
),
'default' => array(
'deft' => array(
'one' => 2,
'two' => 3,
),
'deft_one' => array(
'one' => 't',
'two' => 'h',
),
),
),
);
echo "<pre>";
$it = new RecursiveIteratorIterator(new RecursiveArrayIterator($data));
foreach($it as $var)
{
echo $var , PHP_EOL ;
}
Output
Subscriber
1
1
2
3
t
h
I didn't test it but you can get the idea;
function printArr($obj){
if(!is_array($obj)){
echo $obj;
return;
}
else if(is_array($obj)){
foreach ($obj as $key => $value) {
printArr($obj[$key]);
}
}
}

Categories