Loop through SQL and calculate sum in PHP - php

I have an issue with my code. I have 2 tables. First employee_id:
|Employee id|
1
2
3
And the second table called employee_times:
|Employee_id|Hours_dev|hours_pm|
|1|2|3|
|1|3|4|
|2|3|3|
What I am trying to do is to calculate the total time that each employee has worked (hours_dev+hours_pm). For example employee_id 1 has worked 12 hours
So far I have tried to retrieve all the employee_id from the first table and use a for loop to go through the employee_times in an SQL statement (SEE CODE BELOW). However the code does not work as it prints 0 for both employee_id and total_hours.
I am using MYSQL on a localhost server.
$sql = "SELECT employee_id FROM employee";
$result = mysql_query($sql);
while($row = mysql_fetch_array)
{
$employee_id = $row['employee_id'];
}
$employee_id_length = sizeof($employee_id);
for($i = 0; $i < $employee_id_length; $i++)
{
$sql4 = "SELECT employee_id, hours_dev, hours_pm FROM employee_times WHERE employee_id= '$employee_id[$i]'";
$result = mysql_query($sql4);
while($info = mysql_fetch_array($result));
{
$employee_id = $info['employee_id'];
$hours_dev=$info['hours_dev'];
$hours_pm=$info['hours_pm'];
$total_hours = ($total_hours + $hours_dev + $hours_pm );
}
//print "$employee_id worked for $total_hours";
}
Any help is much appreciated.

you can get sum directly
select employee_id, sum(hours_dev)+ sum(hours_pm) as total
from employee_times WHERE employee_id= '1'
group by employee_id
refer this Fiddle Demo

this should get the data you need
SELECT
hours_dev,
hours_pm,
sum(hours_dev) + sum(hours_pm) as total_hours
FROM
employee_times
WHERE
employee_id = 123
GROUP BY
employee_id

Take a look at aggregate functions:
http://www.w3schools.com/sql/sql_functions.asp
http://www.w3schools.com/sql/sql_func_sum.asp

This SQL query should pull the info much quicker than by script;
SELECT Employee_id, SUM(Hours_dev), SUM(Hours_pm), SUM(Hours_dev + Hours_pm)
FROM employee_times
GROUP BY Employee_id

Related

SUM of columns while grouping by other column

So this is the structure of my MySQL table that I wanna work this out with:
ID type category_id amount
12 Expense 3 963.39
13 Expense 5 1200.50
14 Expense 3 444.12
15 Expense 5 1137.56
..............................
Desired output:
1407,41 (for category_id = 3)
2338,06 (for category_id = 5)
....... (and for other category_id)
What I get now:
1407,41 (only for category_id = 3)
My query does not add or display the sum of other category_id.
This is the query I am trying:
$query = "SELECT SUM(amount) AS TotalAmount FROM spendee WHERE type = 'Expense'
group by category_id having count(*) >1 ";
$expense_query = mysqli_query($connection, $query);
$expense_count = mysqli_fetch_array($expense_query);
echo $expense_count[0];
Been stuck with this for the last couple of days. Any help is very much appreciated. Thank you!
You're only calling mysqli_fetch_array() once. You need to call it in a loop to get all the totals. You should also include the category ID in the SELECT list.
$query = "SELECT category_id, SUM(amount) AS TotalAmount FROM spendee WHERE type = 'Expense'
group by category_id having count(*) >1 ";
$expense_query = mysqli_query($connection, $query);
while ($row = mysqli_fetch_assoc($expense_query)) {
echo "{$row['TotalAmount']} (for category_id = {$row['category_id']}<br>\n";
}
The query here works. It's just that you only select the first result from the $expense_count variable. $expense_count[1] will return the second category listed, $expense_count[2 will return the third one, ect...
Try echo implode(" <br>", $expense_count);
Have a nice day.

php - mysqli count rows with specific value

At the moment I'm able to count all the record's in a table with the value "Waiting". This is done by using:
$query = "SELECT COUNT(*) AS SUM FROM jobs WHERE status='Waiting'";
When I want to echo the row count I just do:
echo $rows['SUM'];
How can I do it so it also count's all the record's in a table with the value "Ready"?
This query will return all status count divided by status:
SELECT status, COUNT(status) AS tot FROM jobs GROUP BY status
The resulting set is something like this:
status tot
----------- ------
Waiting 123
Ready 80
... 56
So you want status='Waiting' or status='Ready'? You can separate parameters with OR or AND; for example:
$query = "SELECT COUNT(*) AS SUM FROM jobs WHERE status='Waiting' OR status='Ready'";
SELECT count(status) AS 'count' FROM jobs GROUP BY status HAVING status='Ready'
This will count the records with the status = Ready. You use GROUP BY to get an aggregate on the status field. And because you have used GROUP BY, you use HAVING (which is the equivalent of WHERE in GROUP situations) to filter the data.
By using IN operator in your query.
$query = "SELECT COUNT(*) AS SUM FROM jobs WHERE status IN ('Waiting','Ready')";
Get group based(status) counts by using GROUP BY operator
$query = "SELECT COUNT(*) AS SUM FROM jobs GROUP BY status";
Print the status based result.
//Create the `mysqli_connection` and assign to `$conn` variable.
$result = mysqli_query($conn, $query);
if($result->num_rows>0)
{
while($row = mysqli_fetch_assoc($result))
{
echo "<br>status=" . $row['status'];
echo "<br>SUM=" . $row['SUM'];
}
}

PHP Calculate rank from database

I got a little problem, I've got a database, in that database are different names, id, and coins. I want to show people their rank, so your rank has to be 1 if you have the most coins, and 78172 as example when your number 78172 with coins.
I know I can do something like this:
SELECT `naam` , `coins`
FROM `gebruikers`
ORDER BY `coins` DESC
But how can I get the rank you are, in PHP :S ?
You can use a loop and a counter. The first row from MySql is going the first rank,I.e first in the list.
I presume you want something like:
1st - John Doe
2nd - Jane Doe
..
..
right?
See: http://www.if-not-true-then-false.com/2010/php-1st-2nd-3rd-4th-5th-6th-php-add-ordinal-number-suffix
Helped me a while ago.
You could use a new varariable
$i = "1";
pe care o poti folosi in structura ta foreach,while,for,repeat si o incrementezi mereu.
and you use it in structures like foreach,while,for,repeat and increment it
$i++;
this is the simplest way
No code samples above... so here it is in PHP
// Your SQL query above, with limits, in this case it starts from the 11th ranking (0 is the starting index) up to the 20th
$start = 10; // 0-based index
$page_size = 10;
$stmt = $pdo->query("SELECT `naam` , `coins` FROM `gebruikers` ORDER BY `coins` DESC LIMIT {$start}, {$page_size}");
$data = $stmt->fetchAll();
// In your template or whatever you use to output
foreach ($data as $rank => $row) {
// array index is 0-based, so add 1 and where you wanted to started to get rank
echo ($rank + 1 + $start) . ": {$row['naam']}<br />";
}
Note: I'm too lazy to put in a prepared statement, but please look it up and use prepared statements.
If you have a session table, you would pull the records from that, then use those values to get the coin values, and sort descending.
If we assume your Session table is sessions(session_id int not null auto_increment, user_id int not null, session_time,...) and we assume that only users who are logged in would have a session value, then your SQL would look something like this: (Note:I am assuming that you also have a user_id column on your gebruikers table)
SELECT g.*
FROM gebruikers as g, sessions as s WHERE s.user_id = g.user_id
ORDER BY g.coins DESC
You would then use a row iterator to loop through the results and display "1", "2", "3", etc. The short version of which would look like
//Connect to database using whatever method you like, I will assume mysql_connect()
$sql = "SELECT g.* FROM gebruikers as g, sessions as s WHERE s.user_id = g.user_id ORDER BY g.coins DESC";
$result = mysql_query($sql,$con); //Where $con is your mysql_connect() variable;
$i = 0;
while($row = mysql_fetch_assoc($result,$con)){
$row['rank'] = $i;
$i++;
//Whatever else you need to do;
}
EDIT
In messing around with a SQLFiddle found at http://sqlfiddle.com/#!2/8faa9/6
I came accross something that works there; I don't know if it will work when given in php, but I figured I would show it to you either way
SET #rank = 0; SELECT *,(#rank := #rank+1) as rank FROM something order by coins DESC
EDIT 2
This works in a php query from a file.
SELECT #rank:=#rank as rank,
g.*
FROM
(SELECT #rank:=0) as z,
gebruikers as g
ORDER BY coins DESC
If you want to get the rank of one specific user, you can do that in mysql directly by counting the number of users that have more coins that the user you want to rank:
SELECT COUNT(*)
FROM `gebruikers`
WHERE `coins` > (SELECT `coins` FROM `gebruikers` WHERE `naam` = :some_name)
(assuming a search by name)
Now the rank will be the count returned + 1.
Or you do SELECT COUNT(*) + 1 in mysql...

Best way to sum and seperate by date in MYSQL with/witout php

Hi i have such table information:
what i want to do with php with while or just in mysql, is to SUM (time_used) of the rows with status 44 until its reached row with status 55. after that it should begin from start with new summing.
first query should return 37, second 76 (keep in mind it should be universal, for unlimited occurrences of 55 status row)
i thought of a way with time/date filtering and have this:
select sum(time_used) as sumed
from timelog
where start_time > (select end_time from timelog where (status='55')
ORDER BY id DESC LIMIT 1) ORDER BY id DESC
but this works only for last combination of 44 and 55
i know i will need two way filtering( < end_time and > end_time) so it will work for all cases, but cant think of a way to do it in php
can anyone help me?
EDIT:
sqlfiddle whoever want it:
http://sqlfiddle.com/#!2/33820/2/0
There are two ways to do it: Plain SQL or PHP. If you treat thousands of rows, it may be interresting to choose between the two by testing performance.
Plain SQL
select project_id, task_id, user_id, sum(time_used) as time_used,
min(start_time) as start_time, max(end_time) as end_time, max(comment) as comment from
(select t.id, t.project_id, t.task_id, t.user_id, t.time_used,
count(t2.id) as count55, t.start_time, t.end_time, t.comment
from timelog t
left join timelog t2 on t.id>t2.id and t2.status=55 and t.task_id=t2.task_id
group by t.id) as t
group by count55;
I assume here that a task can belong to one user only
SQL and PHP
$link = mysqli_connect( ... );
$query = "select id, project_id, task_id, user_id, time_used, start_time, end_time, status
from timelog order by id";
$result = mysqli_query($link, $query);
$table = array();
$time_used = 0;
$start_sum = true;
$i = 0;
while($row = mysqli_fetch_assoc ($result)){
if($start_sum){
$table[$i] = $row;
$start_sum = false;
} else {
$table[$i]['time_used'] += $row['time_used'];
$table[$i]['end_time'] += $row['end_time'];
}
if($row['state'] == 55){
$i++;
$start_sum = true;
}
}
If two tasks can run in simultaneously, solution 1 will work, but solution 2 will need to be adapted in order to take this in account.
here is my intepretation:
http://sqlfiddle.com/#!2/33820/45
set #n=0;
select project_id, task_id, user_id,sum(time_used) from (
SELECT time_used,project_id, task_id, user_id,
#n:=if(status=55,#n+1,#n),
if(status=55,-1,#n) as grouper FROM timelog
) as t
where grouper>-1
group by grouper;
I'm neither a php nor MySQL programmer, but I can explain the logic you want to follow. You can then code it.
First, query your db and return the results to php.
Next, set two sum variables to 0.
Start looping through your query results. Increment the first sum variable until you reach the first row that has status 55. Once you do, start incrementing the second variable.
The tricky part will be to sort your query by the row number of the table. Here is a link that will help you with that part.

PHP SUM function

I have a table like following:
id q_id value
------------------------
1 2 5
2 2 NULL
3 2 5
4 2 NULL
5 4 2
6 4 NULL
7 4 2
8 4 NULL
What I want is to get the sum of (for example) all value where q_id = 2
$sq = mysql_query("SELECT SUM(value) AS sum FROM table WHERE q_id = 2)or die(mysql_error());
while($row = mysql_fetch_array($sq)){
$sum = $row['sum'];
}
echo $sum."<br>";
But I'm getting
5
5
But what I want is the sum of the value and expecting 10 instead.
Thank you for helping.
If you're going to loop over the result set anyway, why not just use
SELECT value FROM table WHERE q_id=2
then sum up those values using the while loop? Something like:
while($row = mysql_fetch_array($sq)) {
    $sum += $row['value'];
}
echo $sum."<br>";
Edit: also, as Jason McCreary said above, you should look into an alternate method of querying the database. I would suggest searching php.net for "PDO", which is very easy to use.
We can directly sum in the query like
SELECT 5+6 AS addition
Give it a try... You are displaying value, there was missing quote in your code.
$sq = mysql_query("SELECT SUM(value) AS sum FROM `table` WHERE `q_id` = '2'")or die(mysql_error());
while($row = mysql_fetch_assoc($sq))
{
$sum = $row["sum"];
}
echo $sum . "<br>";
$sq="SELECT value FROM table WHERE q_id='".$am."'";
$result=mysqli_query($link,$sq);
while($row=mysqli_fetch_assoc($result)) {
$sum += $row['value'];
}
echo "<p>Sum: ".$sum."</p><br>";
//$am ='2';
//$link -- connection to the data base
Please put $am ='2'; before the select statement and also make sure you have connected to the data base using $link
You will get the total sum according to the value of q_id
I have tested the code and works fine.
You need to add a GROUP BY to your query. Add the following to the end
GROUP BY q_id

Categories