Receive quantity of lines of query - sql

Promt please.
I have an query: SELECT MAX(FPS.EndDateKey) WHERE FPS.EndDateKey <>-2
I need to receive quantity of lines of this query in other query:
SELECT INVS.ParticipantKey, MIN(CASE WHEN FPS.EndDateKey <> -2 AND FPS.EndDateKey > FPS.DefinedEndDateKey
AND FPS.EndDateKey > #PeriodEndDateKey AND FPS.DefinedEndDateKey < #PeriodEndDateKey
THEN 1
ELSE 0
END) as InRunout,
MAX(CASE WHEN DP.AccountKey = 6 THEN 1 ELSE 0 END) as HasHSA,
MAX(FPS.StartDateKey) as MostCurrentEnrollment,
CASE WHEN EXISTS(SELECT MAX(FPS.EndDateKey) WHERE FPS.EndDateKey <>-2) THEN 1 ELSE 0 END AS CurrentPlanYear
FROM SupportFile.InvoicableSubscription as INVS
INNER JOIN Evolution1.FactProductSubscription as FPS ON FPS.SubscriptionKey = INVS.SubscriptionKey AND FPS.StartDateKey = INVS.StartDateKey
INNER JOIN Evolution1.DimProduct as DP ON DP.ProductKey = FPS.ProductKey
GROUP BY INVS.ParticipantKey, FPS.EndDateKey
How I am able to do it? Prompt please. Thanks

You can achieve this via a subquery:
Psuedo code:
Select Name, description,
(select max(field) from table2) as maxtable2
from table 1

Related

Sum a column and perform more calculations on the result? [duplicate]

This question already has an answer here:
How to use an Alias in a Calculation for Another Field
(1 answer)
Closed 3 years ago.
In my query below I am counting occurrences in a table based on the Status column. I also want to perform calculations based on the counts I am returning. For example, let's say I want to add 100 to the Snoozed value... how do I do this? Below is what I thought would do it:
SELECT
pu.ID Id, pu.Name Name,
COUNT(*) LeadCount,
SUM(CASE WHEN Status = 'Working' THEN 1 ELSE 0 END) AS Working,
SUM(CASE WHEN Status = 'Uninterested' THEN 1 ELSE 0 END) AS Uninterested,
SUM(CASE WHEN Status = 'Converted' THEN 1 ELSE 0 END) AS Converted,
SUM(CASE WHEN SnoozedId > 0 THEN 1 ELSE 0 END) AS Snoozed,
Snoozed + 100 AS Test
FROM
Prospects p
INNER JOIN
ProspectsUsers pu on p.OwnerId = pu.SalesForceId
WHERE
p.Store = '108'
GROUP BY
pu.Name, pu.Id
ORDER BY
Name
I get this error:
Invalid column name 'Snoozed'.
How can I take the value of the previous SUM statement, add 100 to it, and return it as another column? What I was aiming for is an additional column labeled Test that has the Snooze count + 100.
You can't use one column to create another column in the same way that you are attempting. You have 2 options:
Do the full calculation (as #forpas has mentioned in the comments above)
Use a temp table or table variable to store the data, this way you can get the first 5 columns, and then you can add the last column or you can select from the temp table and do the last column calculations from there.
You can not use an alias as a column reference in the same query. The correct script is:
SELECT
pu.ID Id, pu.Name Name,
COUNT(*) LeadCount,
SUM(CASE WHEN Status = 'Working' THEN 1 ELSE 0 END) AS Working,
SUM(CASE WHEN Status = 'Uninterested' THEN 1 ELSE 0 END) AS Uninterested,
SUM(CASE WHEN Status = 'Converted' THEN 1 ELSE 0 END) AS Converted,
SUM(CASE WHEN SnoozedId > 0 THEN 1 ELSE 0 END)+100 AS Snoozed
FROM
Prospects p
INNER JOIN
ProspectsUsers pu on p.OwnerId = pu.SalesForceId
WHERE
p.Store = '108'
GROUP BY
pu.Name, pu.Id
ORDER BY
Name
MSSQL does not allow you to reference fields (or aliases) in the SELECT statement from within the same SELECT statement.
To work around this:
Use a CTE. Define the columns you want to select from in the CTE, and then select from them outside the CTE.
;WITH OurCte AS (
SELECT
5 + 5 - 3 AS OurInitialValue
)
SELECT
OurInitialValue / 2 AS OurFinalValue
FROM OurCte
Use a temp table. This is very similar in functionality to using a CTE, however, it does have different performance implications.
SELECT
5 + 5 - 3 AS OurInitialValue
INTO #OurTempTable
SELECT
OurInitialValue / 2 AS OurFinalValue
FROM #OurTempTable
Use a subquery. This tends to be more difficult to read than the above. I'm not certain what the advantage is to this - maybe someone in the comments can enlighten me.
SELECT
5 + 5 - 3 AS OurInitialValue
FROM (
SELECT
OurInitialValue / 2 AS OurFinalValue
) OurSubquery
Embed your calculations. opinion warning This is really sloppy, and not a great approach as you end up having to duplicate code, and can easily throw columns out-of-sync if you update the calculation in one location and not the other.
SELECT
5 + 5 - 3 AS OurInitialValue
, (5 + 5 - 3) / 2 AS OurFinalValue
You can't use a column alias in the same select. The column alias do not precedence / sequence; they are all created after the eval of the select result, just before group by and order by.
You must repeat code :
SELECT
pu.ID Id,pu.Name Name,
COUNT(*) LeadCount,
SUM(CASE WHEN Status = 'Working' THEN 1 ELSE 0 END) AS Working,
SUM(CASE WHEN Status = 'Uninterested' THEN 1 ELSE 0 END) AS Uninterested,
SUM(CASE WHEN Status = 'Converted' THEN 1 ELSE 0 END) AS Converted,
SUM(CASE WHEN SnoozedId > 0 THEN 1 ELSE 0 END) AS Snoozed,
SUM(CASE WHEN SnoozedId > 0 THEN 1 ELSE 0 END)+ 100 AS Test
FROM
Prospects p
INNER JOIN
ProspectsUsers pu on p.OwnerId = pu.SalesForceId
WHERE
p.Store = '108'
GROUP BY
pu.Name, pu.Id
ORDER BY
Name
If you don't want to repeat the code, use a subquery
SELECT
ID, Name, LeadCount, Working, Uninterested,Converted, Snoozed, Snoozed +100 AS test
FROM
(SELECT
pu.ID Id,pu.Name Name,
COUNT(*) LeadCount,
SUM(CASE WHEN Status = 'Working' THEN 1 ELSE 0 END) AS Working,
SUM(CASE WHEN Status = 'Uninterested' THEN 1 ELSE 0 END) AS Uninterested,
SUM(CASE WHEN Status = 'Converted' THEN 1 ELSE 0 END) AS Converted,
SUM(CASE WHEN SnoozedId > 0 THEN 1 ELSE 0 END) AS Snoozed
FROM Prospects p
INNER JOIN ProspectsUsers pu on p.OwnerId = pu.SalesForceId
WHERE p.Store = '108'
GROUP BY pu.Name, pu.Id) t
ORDER BY Name
or a view

How to write case when statement to see if sum of 2 values equal?

I am still learning sql so I apologize if this is easy stuff.
I need the sql code to sum the sales amount and sum the returnamount, and if they equal I want to mark that accountnumber with a 1 to know that it is fully cancelled.
i.[status], i.accountnumber,
case when sum(i.saleamount) = sum(r.returnamount) then 1 else 0 end as full_return_flag
from [idtable] i
join [returntable] r on r.id = i.id
> Account Number Sale Amount Return Amount Full_return_flag Status
> 1 500 250 1 Open
> 2 500 1500 1 Open
> 3 2000 0 0 Neutral
> 4 100 0 0 Closed
You want aggregation with case expression :
select i.status, i.accountnumber, sum(i.saleamount) as saleamount, sum(r.returnamount) as returnamount,
(case when sum(i.saleamount - r.returnamount) = 0 then 1 else 0 end) as Full_return_flag
from idtable] i inner join
returntable r
on r.id = t.id
group by i.status, i.accountnumber;
You need a full query:
select i.accountnumber,
sum(i.saleamount) as sale_amount, sum(r.returnamount) as return_amount,
(case when sum(i.saleamount) = sum(r.returnamount) then 1 else 0 end) as full_return_flag
from [idtable] i left join
[returntable] r
on r.id = i.id
group by i.accountnumber;
status is not in the result set so I don't think it is needed in the query. But you can include it both in the select and group by if you need it.

SQL MAX value of two sub queries

I have two queries and I want to get the maximum value of the two of them.
MAX((SELECT COUNT(p.[ItemID]) FROM [dbo].[Table] p WHERE HasHuman=0),
(SELECT COUNT(p.[ItemID]) FROM [dbo].[Table] p WHERE HasHuman=1))
You can calculate both result in a single query and then apply TOP:
select top 1
HasHuman,
COUNT(p.[ItemID]) as cnt
from [dbo].[Table]
group by HasHuman
order by cnt desc
You could even do this in a single query:
SELECT
CASE WHEN SUM(CASE WHEN HasHuman=0 THEN 1 ELSE 0 END) >
SUM(CASE WHEN HasHuman=1 THEN 1 ELSE 0 END)
THEN SUM(CASE WHEN HasHuman=0 THEN 1 ELSE 0 END)
ELSE SUM(CASE WHEN HasHuman=1 THEN 1 ELSE 0 END) END
FROM [dbo].[Table]
WHERE ItemID IS NOT NULL -- you were not counting NULLs
SELECT MAX(RC)
FROM (SELECT COUNT(p.ItemID) AS RC FROM dbo.[Table]
WHERE HasHuman=0
UNION
SELECT COUNT(p.ItemID) AS RC FROM dbo.[Table]
WHERE HasHuman=1
) A

Trying to get count of votes in SQL based on ID

Table structures:
Solution_Votes:
ID int
SolutionID string
Vote int
Solution:
ID int
Solution
VotesUp
VotesDown
Code:
SELECT
*,
(SELECT SUM(CASE WHEN voteUp = 1 THEN 1 ELSE 0 END)
FROM Solutions_Votes) AS VoteCountUp,
(SELECT SUM(CASE WHEN voteDown = 0 THEN 1 ELSE 0 END)
FROM Solutions_Votes) AS VoteCountDown
FROM
Solution
When I run this query it gives me the count on each row for voteUpCount and voteDownCount. I need the count to be based on the solution ID so that each solution has its count of up votes and down votes. If anybody can help it would be appreciated. Thanks in advance!
Just use conditional aggregation. In your case this is simple:
select sv.solutionid,
sum(case when sv.voteUp = 1 then 1 else 0 end) as VoteCountUp,
sum(case when sv.voteDown = 0 then 1 else 0 end) as VoteCountDown
from solutions_votes sv
group by sv.solutionid;
You only need the solutions table if some solutions have no votes and you want to include them.
EDIT:
You would include solutions in various way. Here is one:
select s.*, ss.VoteCountUp, ss.VoteCountDown
from solutions s left join
(select sv.solutionid,
sum(case when sv.voteUp = 1 then 1 else 0 end) as VoteCountUp,
sum(case when sv.voteDown = 0 then 1 else 0 end) as VoteCountDown
from solutions_votes sv
group by sv.solutionid
) ss
on s.solutionid = ss.solutionid;

How to save in a variable the value of the following query? SQL Server

I need to implement two variables for save the data result in a query.
I have he following query:
SELECT * FROM
(SELECT location AS Location, COUNT(*) AS Trucks FROM Truck GROUP BY location) loc
OUTER APPLY
(
SELECT
COUNT(*) AS TotalOfCampaings,
SUM(CASE WHEN cc.campaing_status = 'Complete' THEN 1 ELSE 0 END) AS CampaingsWithCompleteStatus,
SUM(CASE WHEN cc.campaing_status = 'InProcess' THEN 1 ELSE 0 END) AS CampaingsWithInProcessStatus
FROM CampaingControl cc INNER JOIN Truck t ON cc.vin = t.vin
WHERE t.location = loc.location
) stat
This query shows the next table:
|Location|Trucks|TotalOfCampaings|CampaingsWithCompleteStatus|CampaingsWithInProcessStatus
I need to add a column at the end, in the new column i need to get the percent of campaings with complete status, i tried to do something like this:
Percent = (CampaingsWithCompleteStatus / TotalOfCamapings) * 100
But i dont know how to save the values of the query to do that.
Something like this:
SELECT
loc.Location,
loc.Trunks,
stat.TotalOfCampaings,
stat.CampaingsWithCompleteStatus,
stat.CampaingsWithInProcessStatus,
(1.0 * stat.CampaingsWithCompleteStatus /stat.TotalOfCampaings) * 100 as [Percent]
FROM
(SELECT location AS Location, COUNT(*) AS Trucks FROM Truck GROUP BY location) loc
OUTER APPLY
(
SELECT
COUNT(*) AS TotalOfCampaings,
SUM(CASE WHEN cc.campaing_status = 'Complete' THEN 1 ELSE 0 END) AS CampaingsWithCompleteStatus,
SUM(CASE WHEN cc.campaing_status = 'InProcess' THEN 1 ELSE 0 END) AS CampaingsWithInProcessStatus
FROM CampaingControl cc INNER JOIN Truck t ON cc.vin = t.vin
WHERE t.location = loc.location
) stat