Reputation: 49
I wrote the below query which shows me ApplicationIDs associated with two specific ables. I need the results to return the number of times each Applications.AppID appears in those tables next to the row with the application name. Ive used distinct because in my results I only want the name to appear once but have a number next to it indicating how many times it has been used. Examples below. Ive written count conditions before but only for single tables.
SELECT 0 AppId ,
'Select an Application' ApplicationName
union all
select .1 ,
'--All--'
union all
SELECT DISTINCT
Applications.AppId ,
Applications.ApplicationName
FROM ImpactedApplications ,
SupportingApplications
JOIN applications ON SupportingApplications.Appid = applications.appid
JOIN ImpactedApplications Apps on SupportingApplications.AppId = Applications.AppId
Returns something like this:
0.0 Select an Application
0.1 --All--
12.0 APP A
59.0 APP B
60.0 APP C
71.0 APP D
74.0 APP E
121.0 APP F
124.0 APP G
130.0 APP H
I want it to return something like this:
0.0 Select an Application
0.1 --All--
12.0 APP A 1
59.0 APP B 2
60.0 APP C 1
71.0 APP D 4
74.0 APP E 3
121.0 APP F 1
124.0 APP G 2
130.0 APP H 2
Any help is appreciated thank you.
Adding Results from Help Query
12 APP A 17161
59 APP B 51483
60 APP C 85805
71 APP D 17161
Upvotes: 1
Views: 106
Reputation: 74277
First, you do realize that order is unspecified unless you order the result set using order by
? That means there is no guarantee that the first two selects in your union all
will come first.
So, let's strip those two out as they are really extraneous to the actual problem. Let us consider the core select
:
select distinct Applications.AppId , Applications.ApplicationName from ImpactedApplications , SupportingApplications JOIN applications ON SupportingApplications.Appid = applications.appid JOIN ImpactedApplications Apps on SupportingApplications.AppId = Applications.AppId
and dissect it.
Problem #1.
select distinct
is often a code smell indicating that you don't have the correct join criteria or you don't correclty understand the cardinality of the relationships involved.
Problem #2.
Indeed, this is the case. You are mixing old-school, pre-ISO/ANSI joins with ISO/ANSI joins. Since the first two tables in the FROM clause are joined pre-ISO/ANSI style, and you have no where
clause with criteria to join them, The above select
statement is exactly identical to
select distinct a.AppId , a.ApplicationName from ImpactedApplications ia cross join SupportingApplications sa join applications a on sa.Appid = a.appid join ImpactedApplications Apps on sa.AppId = a.AppId
I'm pretty sure you didn't intend to generate the cartesian product of the 2 tables. You haven't described the table schema, but my suspicion, from your problem statement
I need the results to return the number of times each Applications.AppID appears in those tables next to the row with the application name.
is that you want something more along these lines:
select AppId = a.AppId ,
AppName = a.ApplicationName ,
ImpactedCount = coalesce( ia.Cnt , 0 ) ,
SupportingCount = coalesce( sa.Cnt , 0 ) ,
Total = coalesce( ia.Cnt , 0 )
+ coalesce( sa.Cnt , 0 )
from Applications a
left join ( select AppId = t.AppId ,
Cnt = count(*)
from ImpactedApplications t
group by t.AppId
) ia on ia.AppId = a.AppId
left join ( select AppId = t.AppId ,
Cnt = count(*)
from SupportingApplications t
group by t.AppId
) sa on sa.AppId = a.AppId
If you want to restrict the results to just those rows with non-zero values, you could change the left join
clauses to join
, but that would mean you would only get those rows that have a non zero value for both. Instead, add a where clause to restrict the result set:
where sa.Cnt > 0
OR ia.Cnt > 0
In addition to filtering out any rows where both counts are zero, it also removes rows where both rows have a null
count, indicating that no match occurred in the left join
.
Upvotes: 0
Reputation: 60472
DISTINCT is logically equivalent to a GROUP BY:
SELECT Applications.AppId, Applications.ApplicationName
,COUNT(*)
FROM SupportingApplications
INNER JOIN applications ON SupportingApplications.Appid = applications.appid
INNER JOIN ImpactedApplications as Apps on SupportingApplications.AppId = Applications.AppId
GROUP BY Applications.AppId, Applications.ApplicationName
Upvotes: 1
Reputation: 5580
SELECT 0 AppId, 'Select an Application' ApplicationName union all
select .1,'--All--' union all
SELECT DISTINCT app.AppId, app.ApplicationName,count(app.AppId)
FROM SupportingApplications sa
INNER JOIN applications app ON sa.Appid = applications.appid
--INNER JOIN ImpactedApplications as Apps on sa.AppId = app.AppId
group by app.AppId, app.ApplicationName
It doesn't look like your doing anything with ImpactedApplications table, so idk maybe remove that line
Upvotes: 0