Suppose i have following table
id Salary
1 5
2 3
1 3
1 6
2 5
3 5
3 2
4 1
4 3
2 9
I want to get the id of highest total(sum) salary from all groups. In this case the result should be id=2 sum=17( i.e. 3+5+9 = 17)
If you really only expect/need a single id group, then using LIMIT is probably the most straightforward approach here:
SELECT id, SUM(Salary) AS total
FROM yourTable
GROUP BY id
ORDER BY SUM(Salary) DESC
LIMIT 1;
If there could be ties for the highest salary, then we would need to do more work. Before MySQL 8+, the query given by #MKhalid is what we would need to do. Starting with MySQL 8+, we can use the RANK analytic function:
SELECT id, total
FROM
(
SELECT id, SUM(Salary) AS total,
RANK() OVER (ORDER BY SUM(salary) DESC) rank
FROM yourTable
GROUP BY id
) t
WHERE rank = 1;
WITH CTEName AS
(SELECT id, SUM(salary) as total_salary from testTable
GROUP BY id )
select top 1 id from CTEName ORDER BY total_salary desc
Related
How to select name with the highest power and highest salary
Id
Name
Salary
1
Kobe
50000
2
Lebron
500099
3
Steph
628228
4
Thompson
50505
5
Shabu
393828
The CTE represents your table. The query you need is the last 3 lines, where it's sorting the output by salary in descending order, then limiting to 1 row.
with salaries as (
select 1 as id, 'Kobe' as name, 50000 as salary union all
select 2, 'Lebron', 1000000 union all
select 3, 'Steph', 222222
)
select name
from salaries
order by salary desc limit 1
Output:
Lebron
UPDATE
Per your comment about using a Max function, here's one way, using a sub-query:
select name
from salaries
where salary = (select max(salary) from salaries);
You can use a sub-query to to so
SELECT
t.name
FROM <your_table_name> t
WHERE t.id =
(SELECT
t1.id
FROM
<your_table_name> t1
ORDER BY t1.salary
DESC LIMIT 1);
EDIT
Or you can just use
SELECT
t1.name
FROM
<your_table_name> t1
ORDER BY t1.salary
DESC LIMIT 1
Expanding on 53RT's comment, for MySQL:
SELECT Name
FROM myTable
ORDER BY Salary DESC
LIMIT 1
i have table emp :
emp_id quantity
1001 21
1001 10
1002 3
1002 5
1004 4
1004 5
1004 8
i want to get the id having 2nd highest sum
so expected output is
1004 17
let me know how can this be done?
SELECT *,
ROW_NUMBER() OVER(ORDER BY sum_col DESC) as rownum
FROM(
select order_id,
sum(quantity) as sum_col
from order1
group by order_id) t
WHERE t.rownum=2
my query is giving error at line: WHERE t.rownum=2
However if i remove this line it works fine.
Let me know how can i put this condition
WITH cte AS ( SELECT emp_id,
SUM(quantity) `sum`,
DENSE_RANK() OVER (ORDER BY SUM(quantity) DESC) `rank`
FROM test
GROUP BY 1 )
SELECT emp_id, `sum`
FROM cte
WHERE `rank` = 2;
DENSE_RANK() needed (not RANK()) because if, for example, there is 2 rows with highest sum then they'll have RANK and DENSE_RANK equal to 1, but for the next sum value DENSE_RANK will be 2 whereas single RANK will be 3.
fiddle
SELECT emp_id, SUM(quantity) as total_sum FROM emp
GROUP BY emp_id
ORDER BY total_sum DESC
LIMIT 1
OFFSET 1
Try the following one:
SELECT emp_id, SUM(quantity) as total_sum FROM emp
GROUP BY emp_id
ORDER BY total_sum DESC
LIMIT 1,1;
I have a clients mysql table and I´d like to get a cumulatie count of clients grouped by month-year.
I have tried the next, but no look:
SELECT DATE_FORMAT(datacad,'%m-%y') AS month-year, count(id) OVER(ORDER BY id) AS cumulative_count
FROM clients;
clients
-------
id datacad
1 2001-10-10
2 2001-10-11
3 2002-11-12
4 2001-12-14
5 2003-12-15
6 2003-12-16
7 2003-12-17
//required result
month-year cumulative_count
----------------------------
10-2001 3
11-2002 4
12-2003 10
Additional Info:
When I use:
SELECT DATE_FORMAT(datacad,'%m-%y') AS label, count(*) as total FROM clients
GROUP BY label
order by datacad
I get:
label,total
03-2011,1
04-2011,1268
05-2011,1365
06-2011,1244
07-2011,1102
08-2011,315
02-2013,1
03-2013,1
03-2014,1
06-2014,1
07-2014,1
01-2017,1
02-2017,1
01-2018,4
05-2018,2
08-2018,1
09-2019,1
04-2020,3
06-2020,1
But when I use:
SELECT DATE_FORMAT(datacad,'%m-%y') AS month_year,
SUM(COUNT(id)) OVER (ORDER BY id) AS cumulative_count
FROM clients
GROUP BY month_year
ORDER BY MIN(datacad);
I get:
month_year,cumulative_count
03-11,1271
04-11,1268
05-11,2636
06-11,3880
07-11,4982
08-11,5297
02-13,5298
03-13,5299
03-14,5300
06-14,5301
07-14,5302
01-17,5303
02-17,5304
01-18,5308
05-18,1270
08-18,5309
09-19,5310
04-20,5313
06-20,5314
The results from both don´t match.
You need a GROUP BY and to SUM() the counts for a cumulative sum:
SELECT DATE_FORMAT(datacad,'%m-%y') AS month_year,
SUM(COUNT(id)) OVER (ORDER BY MIN(datacad)) AS cumulative_count
FROM clients
GROUP BY month_year
ORDER BY MIN(datacad);
I also assume you want the data in date order, so I added an ORDER BY.
I have an SQL table that stores reports. Each row has a customer_id and a building_id and when I have the customer_id, I need to select the latest row (most recent create_date) for each building with that customer_id.
report_id customer_id building_id create_date
1 1 4 1553561789
2 2 5 1553561958
3 1 4 1553561999
4 2 5 1553562108
5 3 7 1553562755
6 3 8 1553570000
I would expect to get report id's 3, 4, 5 and 6 back.
How do I query this? I have tried a few sub-selects and group by and not gotten it to work.
If you are using MySQL 8+, then ROW_NUMBER is a good approach here:
WITH cte AS (
SELECT *, ROW_NUMBER() OVER (PARTITION BY customer_id, building_id
ORDER BY create_date DESC) rn
FROM yourTable
)
SELECT
report_id,
customer_id,
building_id,
create_date
FROM cte
WHERE rn = 1;
If there could be more than one customer/building pair tied for the latest creation date, and you want to capture all ties, then replace ROW_NUMBER with RANK, and use the same query.
Another variation:
SELECT a.*
FROM myTable a
WHERE a.create_date = (SELECT MAX(create_date)
FROM myTable b
WHERE b.customer_id = a.customer_id
AND b.building_id = a.building_id)
Can try doing a search for "effective dated records" to see various approaches.
I found many questions for finding - second max salary for employees. But in all these posts, only salary is selecting.
select max(salary) from user
WHERE salary NOT IN (SELECT max(salary) from user)
I need all users rows having second max salary.
sample user table
id name salary
------------------------------------
1 A 100
2 B 200
3 C 50
4 D 200
5 E 100
and my expected result is,
id name salary
------------------------------------
1 A 100
5 E 100
You could use two subqueries to isolate the second highest salary, e.g.
SELECT id, name, salary
FROM user
WHERE salary = (SELECT MAX(salary) FROM user WHERE salary < (SELECT MAX(salary) FROM user));
Demo
Note that if you are using MySQL 8+, and are open to using analytic functions, then DENSE_RANK really helps here:
WITH cte AS (
SELECT id, name, salary, DENSE_RANK() OVER (ORDER BY salary DESC) dr
FROM user
)
SELECT id, name, salary
FROM cte
WHERE dr = 2;
You can do like below
SELECT *
FROM user
WHERE salary = (SELECT salary
FROM user
GROUP BY salary
ORDER BY salary DESC
LIMIT 1, 1)
you will get 2nd max salary by this query
SELECT salary FROM user ORDER BY salary DESC LIMIT 1, 1;