I have this table
user_id time_completed
4 86.30887
5 57.81364
5 35.50281
5 10.00000
5 74.19355
5 31.91489
6 15.00000
6 20.50000
I need to sum all the time for each user, something like this:
user_id time_completed
4 86.30887
5 209.42489
6 35.50000
This is how I get the first table:
$result = mysql_query ("SELECT user_id,time_completed FROM `mytable` ORDER BY `mytable`.`user_id` ASC;" )
Any idea?
EDIT:
What if I need to replace user_id for the name in the following table (db_users)?
id username
1 admin
2 peter
3 tom
4 user
5 joey
6 helen
EDIT2:
I've modified this table (db_users) and I want country also appears in the query.
id username country
1 admin ES
2 peter IT
3 tom US
4 user GB
5 joey GE
6 helen FR
Like this:
user_id time_completed country
4 86.30887 GB
5 209.42489 GE
6 35.50000 FR
Take a look here: http://sqlfiddle.com/#!2/24d1b/11
you need to use SUM() which is an aggregate function and group them by their user_id
SELECT user_ID, SUM(time_COmpleted) totalTime
FROM tableName
GROUP BY user_ID
SQLFiddle Demo
UPDATE 1
SELECT b.username, SUM(time_COmpleted) totalTime
FROM tableName a
INNER JOIN db_users b
ON a.user_id = b.id
GROUP BY b.username
SQLFiddle Demo
Related
The title makes it sound easy but what I'd like to do is get the last 20 groups from the groups table, ordered by their corresponding users last login date. A group can have one or more users and ultimately what I want to do is find out which groups have had the least user activity and retrieve the last login date.
Here's the query I came up with -
SELECT DISTINCT g.name, user_max.max_login_last_at FROM groups g
LEFT JOIN group_user gu on g.id = gu.group_id
LEFT JOIN (
SELECT MAX(login_last_at) max_login_last_at, u.id
FROM users u GROUP BY id
) AS user_max ON (user_max.id = gu.user_id)
ORDER BY user_max.max_login_last_at ASC
The problem is when I perform the join, it pulls in every group_user record and results in duplicates. I feel like there could be an easy solution to this one but I can't seem to figure it out!
groups table
id name
1 Group 1
2 Group 2
users table
id email login_last_at
1 user1#example.com 2018-10-17 16:08:47
2 user2#example.com 2018-10-02 15:41:53
3 user3#example.com NULL
4 user4#example.com 2018-10-08 12:01:48
5 user5#example.com 2018-10-15 9:24:57
6 user6#example.com 2018-10-17 11:10:58
7 user7#example.com 2018-10-17 15:33:03
group_user table
id group_id user_id
1 1 1
2 2 1
3 1 2
4 1 3
5 1 4
6 2 5
7 1 5
8 2 6
9 1 7
Current example result -
name max_login_last_ts
Group 1 2018-10-02 15:41:53
Group 1 2018-10-08 12:01:48
Group 2 2018-10-15 09:24:57
Group 1 2018-10-15 09:24:57
Group 2 2018-10-17 11:10:58
Group 1 2018-10-17 15:33:03
Group 1 2018-10-17 16:08:47
Group 2 2018-10-17 16:08:47
Group 1 2018-10-18 08:55:17
The problem is as you can see in the result above is that I'm getting all groups, all I really want is the following -
name max_login_last_ts
Group 2 2018-10-17 16:08:47
Group 1 2018-10-18 08:55:17
Thanks in advance!
I think this query will do what you want. There isn't enough data in your sample to replicate your desired results though.
SELECT g.name, MAX(u.login_last_at) AS max_login_last_at
FROM `groups` g
JOIN group_user gu on gu.group_id = g.id
JOIN users u ON u.id = gu.user_id
GROUP BY g.name
ORDER By max_login_last_at DESC
LIMIT 20
Demo on dbfiddle
I have 3 tables which I need to query where I need to group by 2 columns and also join the tables but still return all results.
Users
ID User_name Category Reason Change_date
1 John 1 2 2016-01-05
2 James 3 1 2015-10-02
3 Peter 1 4 2016-01-04
4 Tony 1 4 2016-01-15
5 Fred 1 4 2016-02-25
6 Rick 3 2 2016-04-19
7 Sonia 2 1 2016-10-14
8 Michelle 2 2 2015-11-09
9 Phillip 3 3 2016-03-01
10 Simon 3 3 2016-03-07
Category
ID Category_name
1 User
2 Super user
3 Admin
Reason
ID Reason_name
1 Promotion
2 Upgrade
3 Sponsor
4 Normal
I did some searching and found https://stackoverflow.com/a/28158276/1278201 and modified my query to try and use it:
SELECT category_name, reasons.reason_name, u1.id as user_id, user_name
from users as u1
JOIN (SELECT id from users where users.change_date BETWEEN '2016-01-01'
AND '2016-11-06' group by users.category, users.reason) AS u2
ON u1.id = u2.id
left join reason on u1.reason=category.id
left join category on u1.category=category.id
The results being returned are only using the group by - I should have 8 rows returned but I am only getting 5 which is one for each occurrence of each reason within each category.
My expected outcome is:
category_name reason_name user_id user_name
User Upgrade 1 John
"Upgrade" count 1
Normal 3 Peter
4 Tony
5 Fred
"Normal" count 3
"User" count 4
Super user Promotion 7 Sonia
"Promotion" count 1
"Super user" count 1
Admin Upgrade 6 Rick
"Upgrade" count 1
Sponsor 9 Phillip
10 Simon
"Sponsor" count 2
"Admin" count 3
How can I get all 8 rows returned as well as being able to get counts for each category_name and reason_name?
For what you are looking for in the expected output, this might be what you looking for:
SELECT
Category_name, reason_name, users.ID,User_name
FROM
Users
inner join Category on Category.ID=Users.Category
inner join Reason on Reason.ID=Users.Reason
where users.change_date BETWEEN '2016-01-01' AND '2016-11-06'
SQLFiddle
You shouldn't use GROUP BY in the subquery, because then it only returns one user ID from each group.
In fact, you don't need the subquery at all. You can just use a WHERE clause to select users that meet the change_date criteria.
SELECT category_name, reasons.reason_name, u1.id as user_id, user_name
from users as u1
left join reason on u1.reason=category.id
left join category on u1.category=category.id
where u1.change_date BETWEEN '2016-01-01' AND '2016-11-06'
To get subtotals of the groupings by category and reason, you can use GROUP BY and WITH ROLLUP.
SELECT category_name, reasons.reason_name, u1.id as user_id, user_name, COUNT(*) AS total
from users as u1
left join reason on u1.reason=category.id
left join category on u1.category=category.id
where u1.change_date BETWEEN '2016-01-01' AND '2016-11-06'
GROUP BY category_name, reason_name, user_id WITH ROLLUP
In the script that displays the results, the totals are in the rows where user_id is NULL. The category totals also have reason IS NULL. So you can display these rows appropriately in the script that displays the results. If you really need to do it all in MySQL, you can put the above query in a subquery, and the containing query can test for user_id IS NULL and reason_name IS NULL.
I have read the different answers here on SO, but I am stuck on this question. Please help.
I have this mysql view named "activeuser":
userid COUNT(*) ACRONYM
1 23 admin
2 2 doe
3 4 tompa
12 4 Marre
13 1 Mia
1 2 admin
3 1 tompa
12 1 Marre
13 1 Mia
2 1 doe
3 1 tompa
12 1 Marre
How can I sum the COUNT column so that I get the following wanted result?
userid COUNT(*) ACRONYM
1 25 admin
2 3 doe
3 6 tompa
12 6 Marre
13 1 Mia
EDITED:
I used this query to create the view:
CREATE VIEW activeuser AS
(SELECT boats_comments.userid, COUNT(boats_comments.userid), boats_user.acronym, boats_user.email
FROM boats_comments
INNER JOIN boats_user
ON boats_comments.userid = boats_user.id
GROUP BY boats_comments.userid
ORDER BY COUNT(boats_comments.userid) DESC)
UNION ALL
(SELECT boats_answers.userid, COUNT(boats_answers.userid), boats_user.acronym, boats_user.email
FROM boats_answers
INNER JOIN boats_user
ON boats_answers.userid = boats_user.id
GROUP BY boats_answers.userid
ORDER BY COUNT(boats_answers.userid) DESC)
UNION ALL
(SELECT boats_questions.userid, COUNT(boats_questions.userid), boats_user.acronym, boats_user.email
FROM boats_questions
INNER JOIN boats_user
ON boats_questions.userid = boats_user.id
GROUP BY boats_questions.userid
ORDER BY COUNT(boats_questions.userid) DESC)
My goal is to see which users are the most active by checking the number of comments, questions and answers... but I got stuck...
As the results in your view has duplicates I guess the underlying code for the view is grouping on something it maybe shouldn't be grouping on.
You can get the results you want by applying SUM to it:
select userid, sum("whatever column2 is named") as "Count", Acronym
from activeuser group by userid, Acronym;
select userid, count(*) from activeuser group by userid;
For my database, having these four table
First one, DEPARTMENT
//DEPARTMENT
D# DNAME
------------------
1 RESEARCH
2 IT
3 SCIENCE
Second one, EMPLOYEE
//Employee
E# ENAME D#
-----------------------
1 ALI 1
2 SITI 2
3 JOHN 2
4 MARY 3
5 CHIRS 3
Third, PROJECT
//PROJECT
P# PNAME D#
-----------------------
1 Computing 1
2 Coding 3
3 Researching 3
Fourth, WORKSON
//WORKSON
E# P# Hours
--------------------
1 1 3
1 2 5
4 3 6
So my output should be something like
E# ENAME D# TOTAL HOURS/W
--------------------------------------------
1 ALI 1 8
2 SITI 2 0
3 JOHN 2 0
4 MAY 3 6
5 CHIRS 3 0
Display 0 because the employee has no project to works on.
my currently statement using
SELECT E#,ENAME,D# and sum(Hours) as TOTAL HOURS/W
FROM EMPLOYEE,PROJECT,WORKSON
WHERE EMPLOYEE.P#
no idea how should it select
You should use an left join like this. You only need 2 tables employee and workson.
Try this query:
SELECT e_tbl.E#, e_tbl.ENAME, e_tbl.D#,
coalesce(SUM(w_tbl.Hours), 0) as "Total Hours/W"
FROM
EMPLOYEE e_tbl LEFT JOIN WORKSON w_tbl
ON e_tbl.E# = w_tbl.E#
GROUP BY e_tbl.E#
You need to use GROUP BY and JOINS , in order to achieve your output
SELECT E.E#,
E.ENAME,
E.D#,
sum(Hours) AS TOTAL HOURS/W
FROM Employee AS E
JOIN WORKSON AS W ON E.E# = W.E#
GROUP BY E.E#,
E.ENAME,E.D#
Use this :)
With the given output you do not need to join all the tables, and this could be done by joining employee and works on as
select
e.`E#`,
e.ENAME,
e.`D#`,
coalesce(tot,0) as `TOTAL HOURS/W`
from Employee e
left join
(
select `E#`,
sum(Hours) as tot
from WORKSON
group by `E#`
)w
on w.`E#` = e.`E#`
group by e.`E#`
DEMO
Hello i've a table similar to this one:
id sponsor name
------------------------
1 0 Sasha
2 1 John
3 1 Walter
4 3 Ashley
5 1 Mark
6 4 Alexa
7 3 Robert
8 3 Frank
9 4 Marika
10 5 Philip
11 9 Elizabeth
when i choose an ID (call it MYCHOICE) i want know all the name of people who has sponsor like MYCHOICE... is simply:
select * from tablename where sponsor=MYCHOICE
but... here is the problem... i would know how many people there is in the downline of this results... so... how many records there are with sponsor like each id.
if i choose id 1 result should be
id name downline
----------------------
2 John 0 (noone with sponsor=2)
3 Walter 3 (3 with sponsor=3: ashley, robert, frank)
5 Mark 1 (1 with sponsor=5: philip)
if i choose id 4 result should be
id name downline
----------------------
6 Alexa 0
9 Marika 1 (1 with sponsor=9: Elizabeth)
i try this "bad solution" if mychoice is 1
select sponsor,count(*) as downline from tablename where sponsor in
(select id from tablename where sponsor=1) group by sponsor order by
downline desc
result of this query is
sponsor downline
---------------------
3 3
5 1
there are 2 problems:
- names are not rights and is not that i want
- the count 0 "2|John|0" in the example dont appears
thank u for advice and help, sorry for english,
N.
SELECT child.id,
child.name,
COUNT(grandchild.sponsor) downline
FROM TableName child
INNER JOIN TableName parent
ON child.sponsor = parent.id AND
parent.id = ? -- << user choice
LEFT JOIN TableName grandchild
ON child.id = grandchild.sponsor
GROUP BY child.id, child.name
SQLFiddle Demo
As you can see, the table is joined to itself twice. The first join that uses INNER JOIN gets the records associated with the Sponsor which is your user_choice. The second join which uses LEFT JOIN gets all the records associated with records from your user_choice.