skip null or 0 value while using row_number sql server - sql

i am trying to get row_number from the data, but i want to skip the null or 0 value
DECLARE #ProcessId INT = 6013006
DECLARE #CommHeaderId int
SELECT #CommHeaderId = a.id
FROM EprocUltimate.dbo.commercial_header a
WHERE a.process_id = #ProcessId
SELECT b.rank_quotation, c.rank_nego,
CASE ISNULL(a.quotation_usd, 0) WHEN 0 THEN a.quotation_idr ELSE a.quotation_usd END As Quotation,
CASE ISNULL(a.nego_usd, 0) WHEN 0 THEN a.nego_idr ELSE a.nego_usd END As Nego
FROM EprocUltimate.dbo.commercial_vendor a
INNER JOIN
(
SELECT a.id, ROW_NUMBER() OVER(ORDER BY CASE quotation_usd WHEN 0 THEN quotation_idr ELSE quotation_usd END ASC) AS rank_quotation
FROM EprocUltimate.dbo.commercial_vendor a
WHERE a.commercial_header_id = #CommHeaderId AND a.commercial_admin_bid_evaluation_result = 'Pass'
) b ON a.id = b.id
INNER JOIN
(
SELECT a.id, ROW_NUMBER() OVER(ORDER BY CASE ISNULL(nego_usd, 0) WHEN 0 THEN nego_idr ELSE nego_usd END ASC) AS rank_nego
FROM EprocUltimate.dbo.commercial_vendor a
WHERE a.commercial_header_id = #CommHeaderId AND a.commercial_admin_bid_evaluation_result = 'Pass'
) c ON a.id = c.id
WHERE a.commercial_header_id = #CommHeaderId AND a.commercial_admin_bid_evaluation_result = 'Pass'
ORDER BY b.rank_quotation
heres the result
rank_quotation rank_nego, value1, value2
1 3 775460000.00 770000000.00
2 1 781036525.00 NULL
3 2 786250000.00 NULL
from this query what i want is to get row_numbering the rank_nego with having value first
so the result that i want to achive is
rank_quotation rank_nego, value1, value2
1 1 775460000.00 770000000.00
2 2 781036525.00 NULL
3 3 786250000.00 NULL

You can use a little workaround to have your NULL values as last records in your subquery with the ROW_NUMBER() OVER (ORDER BY ...) as rank_nego
(
SELECT a.id, ROW_NUMBER() OVER(ORDER BY
-- This statement will first sort records having nego_usd and nego_idr as NULL/0 at the end of the list
CASE WHEN ISNULL(nego_usd, 0) = 0 AND ISNULL(nego_idr, 0) = 0 THEN 1 ELSE 0 END ASC,
-- and then sort with the real values
CASE ISNULL(nego_usd, 0) WHEN 0 THEN nego_idr ELSE nego_usd END ASC
) AS rank_nego
FROM EprocUltimate.dbo.commercial_vendor a
WHERE a.commercial_header_id = #CommHeaderId AND a.commercial_admin_bid_evaluation_result = 'Pass'
) c ON a.id = c.id

Related

SQL(POSTGRESQL) how to return sum = 0 when use group by by no data

SELECT DISTINCT o.payment_type,
CASE WHEN SUM(fee_total) > 0 THEN SUM(fee_total) ELSE 0 END
FROM tbl_order AS o
WHERE payment_type IS NOT NULL
AND created_at BETWEEN '2022-09-25' AND '2022-09-25'
GROUP BY o.payment_type
this is the data
"CARD" 47723090
"CASH" 953411890
"TRANSFER" 55470090
"WALLET" 14200000
solution: no data sum return 0, help me, please!!!!!!
You can use count() function to help
example:
tabl.id <>1
select sum(id) from tab1 where id = 1 limit 10;--null
select case when count(1)>0 then sum(id) else 0 end as sm from tab1 where id = 1 limit 10;--0
select case when count(1)>0 then sum(id) else 0 end as sm from tab1 where id = 2 limit 10;--2

Check all values in another column (NULL or NOT NULL ) and return unique records

As you see for cid=1 all date fields are NULL and for cid=3 all date fields are NOT NULL.
I need get unique cids with new field, if all dates are NULL then with "NULL" and if all dates are NOT NULL then with "NOT NULL".
cid - new field
1 - NULL
3 - NOT NULL
You can do this with aggregation and case:
select cid,
(case when count(datecol) = 0 then 'NULL'
when count(datecol) = count(*) then 'NOT NULL'
end) as newField
from t
group by cid
having count(datecol) in (0, count(*));
select cid, case when min(c) = 0 AND max(c) = 0 then 'null' when min(c) = 1 and max(c) = 1 then 'not null' end from (
select cid, case when dt is null then 0 else 1 end as c from your_table
) t
group by cid
having min(c) = max(c)

Sql server aggregate function and GROUP BY Clause error

I have a query below where it compares the number of stagingCabincrew and StagingCockpitCrew columns from the staging schema and compares them to their data schema equivalent 'DataCabinCrew' and 'DataCockpitCrew'.
Below is the query and the results outputted:
WITH CTE AS
(SELECT cd.*,
c.*,
DataFlight,
l.ScheduledDepartureDate,
l.ScheduledDepartureAirport
FROM
(SELECT *,
ROW_NUMBER() OVER(PARTITION BY LegKey
ORDER BY UpdateID DESC) AS RowNumber
FROM Data.Crew) c
INNER JOIN Data.CrewDetail cd ON c.UpdateID = cd.CrewUpdateID
AND cd.IsPassive = 1
AND RowNumber = 1
INNER JOIN
(SELECT *,
Carrier + CAST(FlightNumber AS VARCHAR) + Suffix AS DataFlight
FROM Data.Leg) l ON c.LegKey = l.LegKey )
SELECT StagingFlight,
sac.DepartureDate,
sac.DepartureAirport,
cte.DataFlight,
cte.ScheduledDepartureDate,
cte.ScheduledDepartureAirport,
SUM(CASE
WHEN sac.CREWTYPE = 'F' THEN 1
ELSE 0
END) AS StagingCabinCrew,
SUM(CASE
WHEN sac.CREWTYPE = 'C' THEN 1
ELSE 0
END) AS StagingCockpitCrew,
SUM(CASE
WHEN cte.CrewType = 'F' THEN 1
ELSE 0
END) AS DataCabinCrew,
SUM(CASE
WHEN cte.CrewType = 'C' THEN 1
ELSE 0
END) AS DataCockpitCrew
FROM
(SELECT *,
Airline + CAST(FlightNumber AS VARCHAR) + Suffix AS StagingFlight,
ROW_NUMBER() OVER(PARTITION BY Airline + CAST(FlightNumber AS VARCHAR) + Suffix
ORDER BY UpdateId DESC) AS StageRowNumber
FROM Staging.SabreAssignedCrew) sac
LEFT JOIN CTE cte ON StagingFlight = DataFlight
AND sac.DepartureDate = cte.ScheduledDepartureDate
AND sac.DepartureAirport = cte.ScheduledDepartureAirport
AND sac.CREWTYPE = cte.CrewType
WHERE MONTH(sac.DepartureDate) + YEAR(sac.DepartureDate) = MONTH(GETDATE()) + YEAR(GETDATE())
AND StageRowNumber = 1 --AND cte.ScheduledDepartureDate IS NOT NULL
--AND cte.ScheduledDepartureAirport IS NOT NULL
GROUP BY StagingFlight,
sac.DepartureDate,
sac.DepartureAirport,
cte.DataFlight,
cte.ScheduledDepartureDate,
cte.ScheduledDepartureAirport
The results are correct, all I need to do is add a condition in the WHERE clause where StagingCabinCrew <> DataCabinCrew AND StagingCockpitCrew <> DataCockpitCrew
If a row appears then we have found an error in the data, I just need helping adding this condition in the WHERE Clause because the columns in the WHERE Clause are referring to a SUM and CASE Function. I just need help manipulating the query so that I can add this WHERE Clause
I will guess you are trying to use an alias in the same query.
You CANT do this, because the alias wont be recognized in the WHERE.
SELECT field1 + field2 as myField
FROM yourTable
WHERE myField > 3
You need to include it in a sub query
with cte2 as (
SELECT field1 + field2 as myField
FROM yourTable
)
SELECT *
FROM cte2
WHERE myField > 3
or repeat the function
SELECT field1 + field2 as myField
FROM yourTable
WHERE field1 + field2 > 3

case statement if table present

I am having problem in finding table from different database (table sometimes get dropped due to procedure) if the table is present then condition else direct ans as 1
select (case when exists (select * from SysSet.INFORMATION_SCHEMA .TABLES where TABLE_NAME = 'CHQPASS') then (
case when left(tranm.docu_no,1) <>'3' or tranm.docu_dt <'01/01/2015' then 1
when (select top 1 ACHD_KEY from TRAND k where k.TRN_NO = TRANM.TRN_NO and k.DR_CR ='D' ) = 'A000100010002' THEN 1
WHEN (select COUNT(*) from SYSSET..chqpass D where D.COMP_DIR ='PSAGR' and D.DOCU_DT = TRANM.DOCU_DT and D.AMT = TRAND.TOT_AMT ) <> 0
THEN 1
else cast(isnull (trand.RECONCILE,0)as int)
end)
else 1
end )as pend
if table is not present it show the error
Msg 208, Level 16, State 1, Line 2 Invalid object name
'SYSSET..chqpass'.
table not present how can i stop it to see that table
Replace following line
WHEN (select COUNT(*) from SYSSET..chqpass D where D.COMP_DIR ='xyz' and D.DOCU_DT >'01/01/2015' and D.AMT = 2556 ) <> 0
with this line
WHEN EXEC('(select COUNT(*) from SYSSET..chqpass D where D.COMP_DIR =''xyz'' and D.DOCU_DT >''01/01/2015'' and D.AMT = 2556 )') <> 0
It should work this way...
Try this try replacing the sys.tables with INformationschema so you can specify which schema the table is present in.
SELECT
(
CASE WHEN EXISTS(SELECT * FROM SYSSET.INFORMATION_SCHEMA.TABLES WHERE TABLE_NAME = 'CHQPASS' AND TABLE_SCHEMA = 'dbo')
THEN (
CASE WHEN LEFT(tranm.docu_no,1) <>'3' or tranm.docu_dt < '01/01/2015' THEN 1
WHEN (SELECT TOP 1 ACHD_KEY FROM TRAND k WHERE k.TRN_NO = TRANM.TRN_NO and k.DR_CR ='D' ) = 'A000100010002' THEN 1
WHEN (select COUNT(*) from SYSSET..chqpass D WHERE D.COMP_DIR ='PSAGR' and D.DOCU_DT = TRANM.DOCU_DT and D.AMT = TRAND.TOT_AMT ) <> 0 THEN 1
ELSE cast(isnull (trand.RECONCILE,0)as int)
END
)
ELSE 1
END
) as pend

counting records on the same table with different values possibly none sql server 2008

I have a inventory table with a condition i.e. new, used, other, and i am query a small set of this data, and there is a possibility that all the record set contains only 1 or all the conditions. I tried using a case statement, but if one of the conditions isn't found nothing for that condition returned, and I need it to return 0
This is what I've tried so far:
select(
case
when new_used = 'N' then 'new'
when new_used = 'U' then 'used'
when new_used = 'O' then 'other'
end
)as conditions,
count(*) as count
from myDB
where something = something
group by(
case
when New_Used = 'N' then 'new'
when New_Used = 'U' then 'used'
when New_Used = 'O' then 'other'
end
)
This returns the data like:
conditions | count
------------------
new 10
used 45
I am trying to get the data to return like the following:
conditions | count
------------------
new | 10
used | 45
other | 0
Thanks in advance
;WITH constants(letter,word) AS
(
SELECT l,w FROM (VALUES('N','new'),('U','used'),('O','other')) AS x(l,w)
)
SELECT
conditions = c.word,
[count] = COUNT(x.new_used)
FROM constants AS c
LEFT OUTER JOIN dbo.myDB AS x
ON c.letter = x.new_used
AND something = something
GROUP BY c.word;
try this -
DECLARE #t TABLE (new_used CHAR(1))
INSERT INTO #t (new_used)
SELECT t = 'N'
UNION ALL
SELECT 'N'
UNION ALL
SELECT 'U'
SELECT conditions, ISNULL(r.cnt, 0) AS [count]
FROM (
VALUES('U', 'used'), ('N', 'new'), ('O', 'other')
) t(c, conditions)
LEFT JOIN (
SELECT new_used, COUNT(1) AS cnt
FROM #t
--WHERE something = something
GROUP BY new_used
) r ON r.new_used = t.c
in output -
new 2
used 1
other 0
You can do it as a cross-tab:
select
sum(case when new_used = 'N' then 1 else 0 end) as N,
sum(case when new_used = 'U' then 1 else 0 end) as U,
sum(case when new_used = 'O' then 1 else 0 end) as Other
from myDB
where something = something