SQL Server 2008: Select name of column with greatest recurring value - sql

I am trying to select the name of a field which occurs the most often in a table and in which a certain value is true.
Select
Max(Count(Name))
From
EmployeeTreats
Where
Donut = "Yes"
And
AmountEaten >= 10
Error: Cannot perform an aggregate
function on an expression containing
an aggregate or a subquery.
What I am looking for is obviously something like: Edward has eaten the most with a sum total of 45
Name
Edward

According to your initial question:
select top (1)
[Name]
, count(1) as Cnt
from Employees
where Donut = 'yes'
and AmountEaten >= 10
group by [Name]
order by Cnt desc;
After your edit:
select top (1)
[Name]
, sum(AmountEaten) as TotalEaten
from Employees
where Donut = 'yes'
group by [Name]
order by TotalEaten desc;

This will handle the case where there's more than one Name with the same count.
select Name, count(*)
from ExployeeTreats
where Donut = "Yes" and AmountEaten >= 10
group by Name
having count(*) >= ALL ( select count(*)
from EmployeeTreats
where Donut = "Yes" and AmountEaten >= 30
group by Name )

The trick is to group by name. Then order by count(*) descending, and clip off the top 1.
select top 1 max(name)
from employeeTreats
where donut='Yes'
and amountEaten >= 10
group by name
order by count(*) desc

Related

SUM UP two columns and then find the find MAX value in SQL Server

I am working with Microsoft SQL Server and want to find E_ID and E_Name where T1+T2 has the MAX value.
I have two steps to reach the necessary result:
Find the sum of two columns AS "total" in a table
Find the row that contains the maximum value from total
Table named "table1" looks like the following (T2 may contains NULL values):
E_ID
E_Name
T1
T2
1
Alice
55
50
2
Morgan
60
40
3
John
65
4
Monica
30
10
5
Jessica
25
6
Smith
20
5
Here is what I've tried:
SELECT
E_ID, E_Name, MAX(total) AS max_t
FROM
(SELECT
E_ID, E_Name, ISNULL(T1, 0) + ISNULL(T2, 0) AS total
FROM
table1) AS Q1;
I get this error:
'Q1.E_ID' is invalid in the select list because it is not contained in either an aggregate function or the GROUP BY clause.
I get the result only when I keep MAX(total) AS max_t in the SELECT part but I also want to have the columns E_ID and E_Name.
Try this - just sort by the Total column in a descending fashion, and take the first row in the result:
SELECT TOP (1)
Q1.E_ID, Q1.E_Name, Q1.Total
FROM
(SELECT
E_ID, E_Name, ISNULL(T1, 0) + ISNULL(T2, 0) AS Total
FROM
table1) AS Q1
ORDER BY
Q1.Total DESC;
You can use the query:
SELECT top 1 E_ID, E_Name, (T1+T2) as Total
FROM Table1
GROUP BY E_ID,E_Name
ORDER BY Total desc
SELECT
TOP (1) , E_ID, E_Name, ISNULL(T1, 0) + ISNULL(T2,0) AS Total
FROM
table1
ORDER BY
Total DESC;
If you wanna see all the records you just need to apply the GROUP BY clause.
SELECT
E_ID
, E_Name
, MAX(total) AS max_t
FROM
(SELECT
E_ID
, E_Name
, ISNULL(T1, 0) + ISNULL(T2, 0) AS total
FROM
table1
) AS Q1
GROUP BY
E_ID
, E_Name;
If you want to see only the MAX value in the dataset you just need to apply the TOP 1 (for one record in the result), then sum the T1 and T2 as total and
then apply the ORDER BY DESC;
SELECT TOP 1
E_ID
, E_Name
, (T1 + T2) AS total
FROM
table1
ORDER BY
total DESC
You can do it without subqueries, by ordering purposefully your data:
SELECT TOP 1
E_Name
FROM tab
ORDER BY COALESCE(T1,0)+COALESCE(T2,0) DESC
Check the demo here.

select value based on max of other column

I have a few questions about a table I'm trying to make in Postgres.
The following table is my input:
id
area
count
function
1
100
20
living
1
200
30
industry
2
400
10
living
2
400
10
industry
2
400
20
education
3
150
1
industry
3
150
1
education
I want to group by id and get the dominant function based on max area. With summing up the rows for area and count. When area is equal it should be based on max count, when area and count is equal it should be based on prior function (i still have to decide if education is prior to industry or vice versa). So the result should be:
id
area
count
function
1
300
50
industry
2
1200
40
education
3
300
2
industry
I tried a lot of things and maybe it's easy, but i don't get it. Can someone help to get the right SQL?
One method uses row_number() and conditional aggregation:
select id, sum(area), sum(count),
max(function) over (filter where seqnum = 1) as function
from (select t.*,
row_number() over (partition by id order by area desc) as seqnum
from t
) t
group by id;
Another method uses ``distinct on`:
select id, sum(area) over (partition by id) as area,
sum(count) over (partition by id) as count,
function
from t
order by id, area desc;
Use a scalar sub-query for "function".
select t.id, sum(t.area), sum(t.count),
(
select "function"
from the_table
where id = t.id
order by area desc, count desc, "function" desc
limit 1
) as "function"
from the_table as t
group by t.id order by t.id;
SQL Fiddle
you can use sum as window function:
select distinct on (t.id)
id,
sum(area) over (partition by id) as area,
sum(count) over (partition by id) as count,
( select function from tbl_test where tbl_test.id = t.id order by count desc limit 1 ) as function
from tbl_test t
This is how you get the function for each group based on id:
select id, function
from yourtable yt1
left join yourtable yt2
on yt1.id = yt2.id and yt1.area < yt2.area
where yt2.area.id is null;
(we ensure that no yt2 exists that would be of the same id but of higher areay)
This would work nicely, but you might have several max areas with different values. To cope with this isue, let's ensure that exactly one is chosen:
select id, max(function) as function
from yourtable yt1
left join yourtable yt2
on yt1.id = yt2.id and yt1.area < yt2.area
where yt2.area.id is null
group by id;
Now, let's join this to our main table;
select yourtable.id, sum(yourtable.area), sum(yourtable.count), t.function
from yourtable
join (
select id, max(function) as function
from yourtable yt1
left join yourtable yt2
on yt1.id = yt2.id and yt1.area < yt2.area
where yt2.area.id is null
group by id
) t
on yourtable.id = t.id
group by yourtable.id;

SUM of grouped COUNT in SQL Query

I have a table with 2 fields:
ID Name
-- -------
1 Alpha
2 Beta
3 Beta
4 Beta
5 Charlie
6 Charlie
I want to group them by name, with 'count', and a row 'SUM'
Name Count
------- -----
Alpha 1
Beta 3
Charlie 2
SUM 6
How would I write a query to add SUM row below the table?
SELECT name, COUNT(name) AS count
FROM table
GROUP BY name
UNION ALL
SELECT 'SUM' name, COUNT(name)
FROM table
OUTPUT:
name count
-------------------------------------------------- -----------
alpha 1
beta 3
Charlie 2
SUM 6
SELECT name, COUNT(name) AS count, SUM(COUNT(name)) OVER() AS total_count
FROM Table GROUP BY name
Without specifying which rdbms you are using
Have a look at this demo
SQL Fiddle DEMO
SELECT Name, COUNT(1) as Cnt
FROM Table1
GROUP BY Name
UNION ALL
SELECT 'SUM' Name, COUNT(1)
FROM Table1
That said, I would recomend that the total be added by your presentation layer, and not by the database.
This is a bit more of a SQL SERVER Version using Summarizing Data Using ROLLUP
SQL Fiddle DEMO
SELECT CASE WHEN (GROUPING(NAME) = 1) THEN 'SUM'
ELSE ISNULL(NAME, 'UNKNOWN')
END Name,
COUNT(1) as Cnt
FROM Table1
GROUP BY NAME
WITH ROLLUP
Try this:
SELECT ISNULL(Name,'SUM'), count(*) as Count
FROM table_name
Group By Name
WITH ROLLUP
all of the solution here are great but not necessarily can be implemented for old mysql servers (at least at my case). so you can use sub-queries (i think it is less complicated).
select sum(t1.cnt) from
(SELECT column, COUNT(column) as cnt
FROM
table
GROUP BY
column
HAVING
COUNT(column) > 1) as t1 ;
Please run as below :
Select sum(count)
from (select Name,
count(Name) as Count
from YourTable
group by Name); -- 6
The way I interpreted this question is needing the subtotal value of each group of answers. Subtotaling turns out to be very easy, using PARTITION:
SUM(COUNT(0)) OVER (PARTITION BY [Grouping]) AS [MY_TOTAL]
This is what my full SQL call looks like:
SELECT MAX(GroupName) [name], MAX(AUX2)[type],
COUNT(0) [count], SUM(COUNT(0)) OVER(PARTITION BY GroupId) AS [total]
FROM [MyView]
WHERE Active=1 AND Type='APP' AND Completed=1
AND [Date] BETWEEN '01/01/2014' AND GETDATE()
AND Id = '5b9xxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx' AND GroupId IS NOT NULL
GROUP BY AUX2, GroupId
The data returned from this looks like:
name type count total
Training Group 2 Cancelation 1 52
Training Group 2 Completed 41 52
Training Group 2 No Show 6 52
Training Group 2 Rescheduled 4 52
Training Group 3 NULL 4 10535
Training Group 3 Cancelation 857 10535
Training Group 3 Completed 7923 10535
Training Group 3 No Show 292 10535
Training Group 3 Rescheduled 1459 10535
Training Group 4 Cancelation 2 27
Training Group 4 Completed 24 27
Training Group 4 Rescheduled 1 27
You can use union to joining rows.
select Name, count(*) as Count from yourTable group by Name
union all
select "SUM" as Name, count(*) as Count from yourTable
For Sql server you can try this one.
SELECT ISNULL([NAME],'SUM'),Count([NAME]) AS COUNT
FROM TABLENAME
GROUP BY [NAME] WITH CUBE
with cttmp
as
(
select Col_Name, count(*) as ctn from tab_name group by Col_Name having count(Col_Name)>1
)
select sum(ctn) from c
You can use ROLLUP
select nvl(name, 'SUM'), count(*)
from table
group by rollup(name)
Use it as
select Name, count(Name) as Count from YourTable
group by Name
union
Select 'SUM' , COUNT(Name) from YourTable
I am using SQL server and the following should work for you:
select cast(name as varchar(16)) as 'Name', count(name) as 'Count'
from Table1
group by Name
union all
select 'Sum:', count(name)
from Table1
I required having count(*) > 1 also. So, I wrote my own query after referring some the above queries
SYNTAX:
select sum(count) from (select count(`table_name`.`id`) as `count` from `table_name` where {some condition} group by {some_column} having count(`table_name`.`id`) > 1) as `tmp`;
Example:
select sum(count) from (select count(`table_name`.`id`) as `count` from `table_name` where `table_name`.`name` IS NOT NULL and `table_name`.`name` != '' group by `table_name`.`name` having count(`table_name`.`id`) > 1) as `tmp`;
You can try group by on name and count the ids in that group.
SELECT name, count(id) as COUNT FROM table group by name
After the query, run below to get the total row count
select ##ROWCOUNT
select sum(s) from
(select count(Col_name) as s from Tab_name group by Col_name having count(*)>1)c

SELECT MAX of COUNT

I have a table "well". It contains a column app_rate_unit (type: nvarchar).
My goal is to count every distinct value in the table and let the DBMS (MS Server 2005) give me the most occurring one.
This is my code:
SELECT MAX(app_rate_unit) AS MAX_APP
FROM (SELECT app_rate_unit, COUNT(*) AS co
FROM dbo.well AS w
GROUP BY app_rate_unit
) AS derivedtbl_1
The poblem with it is however, that my DBMS actually delivers the lowest count to me.
SideQuestion: How do I filter for a foreign key (in the table) and NOT NULL (in app_rate_unit) when counting?
select top 1 app_rate_unit, count(*) from dbo.well
group by app_rate_unit
order by count(*) desc
Try this
SELECT
COUNT(app_rate_unit)AS MAX_APP ,
app_rate_unit
FROM
dbo.well
WHERE
app_rate_unit IS NOT NULL
GROUP BY
app_rate_unit
ORDER BY
MAX_APP DESC
The above script will give you the count and the item. You can change the count if you are not sure only one item will have the maximum number of occurrence.
select top 1 count(*) as co from dbo.well as w group by app_rate_unit
order by count(*) desc
In PostgreSQL we can write query which using max of count as
select max(count) from (
select count(id) from Table _name group by created_by,status_id having status_id = 6 ) as Alias
eg
select max(count) from (
select count(id) from orders group by created_by,status_id having status_id = 6 ) as foo

How to sum count value in SQL Server?

How to sum count value in SQL Server ?
I have table 1. I want to sum count value.
How to do that ?
SELECT Top 10 count(d.name) as countname,d.name as name ,sum(count(d.name)) as sumcount
FROM table 1 as d
group by d.name order by count(d.name) desc
I want to display countname, name, sumcount. How to do that ?
Not sure I'm understanding your question, but if you're just looking to get the sum of all the count(d.name) values, then this would do that for you:
select sum(countname) as TotalCount
from
(
SELECT Top 10
count(d.name) as countname,
d.name as name
FROM [table 1] as d
group by d.name
order by count(d.name) desc
)a
add with rollup to the end of your query
Expanding on the answer provided by #Shark, MySQL syntax will look like the following:
set #TotalCount = (select sum(countname) from (
select count(d.name) as countname, d.name as name
from table 1 as d
group by name
order by countname desc
limit 10
) a);
select count(d.name) as countname, d.name as name, #TotalCount
FROM table 1 as d
group by name
order by countname desc
limit 10;
You may need to look up MS SQL syntax for setting local variables and limits.