I can't quite get my conditions correct to alter an existing query that works.
SELECT dd.GasYear,D.DealCash_IsAgency,D.DealCash_IsNetBack, dd.GasYearName,dd.MonthName,dd.Season,dd.FirstOfMonthDate,Deal_OrigDate,DATENAME(WEEKDAY, Deal_OrigDate) AS Orig_DayofWeek
,Deal_StartDate,DATENAME(WEEKDAY, Deal_StartDate) AS Start_DayofWeek,Deal_StopDate,DATENAME(WEEKDAY, Deal_StopDate) AS Stop_DayofWeek
,CASE
WHEN CAST(DATEDIFF(d, Deal_StartDate, Deal_StopDate) AS CHAR(10)) > 6 THEN 'All Other'
END AS DealType
,Deal_Owner,d.Deal_Id,CP_Cmp_ShortName
,CASE
WHEN Qty_MeasurementType_Short = 'GJ' THEN DealCashTran_Qty / 2.055098
ELSE DealCashTran_Qty
END DealCashTran_Dth_Qty
FROM uvDealCash d
LEFT OUTER JOIN uvDealCashTran AS dct
ON d.Deal_Id = dct.Deal_Id
INNER JOIN Cmp c
ON d.CP_Cmp_ShortName = c.Cmp_ShortName
INNER JOIN [uvCmp_CmpType_CmpCPType] ct
ON c.Cmp_Id = ct.Cmp_Id
INNER JOIN BISandbox.dbo.dimDate dd
ON d.Deal_StartDate = dd.FullDate
WHERE ((Deal_Owner IN ('TYK', 'JTT', 'MML', 'CGG', 'LIO', 'MAT')
AND ct.CmpCPType_Descript = 'Producer')
--US Entities Kristen's wants added
OR (CP_Cmp_ShortName IN ('SEV', 'CNAT', 'TNMKT', 'CENT')))
AND Deal_LengthInMonths >= 0
AND DATEDIFF(d, Deal_StartDate, Deal_StopDate) > 6
AND Deal_StartDate > '4/1/2018' --=<Parameters.StartDate>
AND DealPurchaseSellType_Short = 'P'
AND d.DealCashType_Short IN ('DFM', 'FM')
In addition to the above I want to exclude results if DealCash_IsAgency = 1 or D.DealCash_IsNetBack = 1
I tried several variations by adding this to the end of the existing WHERE statement.
--exclude AMA and NB
AND (D.DealCash_IsAgency = 1 OR D.DealCash_IsNetBack = 1)
It still returns rows with 1's in both of the columns.
Greatly appreciate any suggestions.
Thanks
Brent
if you want to exclude then you have to add a condition like this by adding not:
AND NOT (D.DealCash_IsAgency = 1 OR D.DealCash_IsNetBack = 1)
Related
I read a lot of similar questions but didn't find a solution for me. Basically I would like to have a where clause (AND PEKP.VORGANGS_ART = 'BE') only if a special condition (PFSP.EINKAUFS_KZ = 2) is true.
I tried in many ways like that:
SELECT *
FROM PFSP
LEFT OUTER JOIN PFAK on PFSP.RUECKMELDE_NR = PFAK.RUECKMELDE_NR
LEFT OUTER JOIN PEKP ON (PFSP.BESTELL_NR=PEKP.VORGANGS_NR)
AND (PFSP.BESTELL_POS_NR=PEKP.VORGANGS_POS_NR)
LEFT OUTER JOIN PMLB ON PFSP.KOMPONENTEN_ARTIKEL_NR=PMLB.ARTIKEL_NR
WHERE PFAK.KD_VORGANGS_NR = '910-001213'
AND PFSP.RUECKMELDE_STATUS = '3'
AND PFSP.BESCHAFFUNGSKENNER = 'F'
AND CASE PFSP.EINKAUFS_KZ
WHEN 2 THEN PEKP.VORGANGS_ART = 'BE'
END
but I keep getting errors:
wrong syntax near '='"
Skip the CASE, use AND/OR instead:
AND (PFSP.EINKAUFS_KZ <> 2 OR PEKP.VORGANGS_ART = 'BE')
If PFSP.EINKAUFS_KZ = 2, then PEKP.VORGANGS_ART must be equal to 'BE'.
If PFSP.EINKAUFS_KZ <> 2, it doesn't matter what PEKP.VORGANGS_ART is.
With this CASE expression:
AND 1 = CASE
WHEN PFSP.EINKAUFS_KZ = 2 AND PEKP.VORGANGS_ART = 'BE' THEN 1
WHEN PFSP.EINKAUFS_KZ = 2 THEN 0
ELSE 1
END
The order of the conditions is important.
You probably want something like:
AND (
(PFSP.EINKAUFS_KZ = 2 AND PEKP.VORGANGS_ART='BE')
OR PFSP.EINKAUFS_KZ <> 2 --You may need to catch NULL as well
)
SELECT *
FROM PFSP
LEFT OUTER JOIN PFAK on PFSP.RUECKMELDE_NR = PFAK.RUECKMELDE_NR
LEFT OUTER JOIN PEKP ON (PFSP.BESTELL_NR=PEKP.VORGANGS_NR)
AND (PFSP.BESTELL_POS_NR=PEKP.VORGANGS_POS_NR)
LEFT OUTER JOIN PMLB ON PFSP.KOMPONENTEN_ARTIKEL_NR=PMLB.ARTIKEL_NR
WHERE PFAK.KD_VORGANGS_NR = '910-001213'
AND PFSP.RUECKMELDE_STATUS = '3'
AND PFSP.BESCHAFFUNGSKENNER = 'F'
AND ((PFSP.EINKAUFS_KZ = 2 AND PEKP.VORGANGS_ART = 'BE') OR (PFSP.EINKAUFS_KZ <> 2) )
Can anyone help me try to solve this equation? The "Lost_Weight" is a calculation field and I'm trying to get the result of HWeight - renWeight = '0' if the renWeight is 0. The where clause has a controversial statement that put a Challenge to me to make that happen. See below.
SELECT TOP (100) PERCENT dbo.Name.ID,
dbo.Name.CO_ID,
dbo.Name.FULL_NAME,
dbo.Name.STATE_PROVINCE, dbo.Tops_Profile.START_WGHT,
dbo.Tops_Profile.RENEWAL_WEIGHT,
dbo.Tops_Profile.H_WEIGHT - dbo.Tops_Profile.RENEWAL_WEIGHT AS Lost_Weight,
dbo.Tops_Profile.H_WEIGHT,
dbo.Name.JOIN_DATE,
dbo.Name.BIRTH_DATE,
RIGHT(dbo.TOPS_AWARDS.AWARD_TYPE, 15) AS AWARDS_TYPE,
dbo.TOPS_AWARDS.AWARD_CATEGORY,
dbo.TOPS_AWARDS.AWARD_DATE,
dbo.vw_RegDirs.TARGET_ID AS
RD_ID,
dbo.vw_Coords.TARGET_ID AS Coord_ID,
dbo.vw_Coords.FULL_NAME AS
Coord_Name,
dbo.vw_AreaCapts.TARGET_ID AS AC_ID, dbo.Name.STATUS
FROM dbo.Name INNER JOIN dbo.Tops_Profile
ON dbo.Name.ID = dbo.Tops_Profile.ID
INNER JOIN dbo.vw_RegDirs
ON dbo.Name.CO_ID = dbo.vw_RegDirs.CHAPTER
INNER JOIN dbo.vw_Coords
ON dbo.Name.CO_ID = dbo.vw_Coords.CHAPTER
INNER JOIN dbo.vw_AreaCapts
ON dbo.Name.CO_ID = dbo.vw_AreaCapts.CHAPTER
LEFT OUTER JOIN dbo.TOPS_AWARDS
ON dbo.Name.ID = dbo.TOPS_AWARDS.ID
WHERE (dbo.Tops_Profile.RENEWAL_WEIGHT <> '0')
AND (dbo.Name.STATUS = 'a')
AND (dbo.Tops_Profile.H_WEIGHT - dbo.Tops_Profile.RENEWAL_WEIGHT >= 100')
OR (dbo.Name.STATUS = 'a') AND (dbo.TOPS_AWARDS.AWARD_TYPE LIKE '%Century%')
right now if the renewal_weight is 0 it automatically give me the number from the H_WEIGHT in the Lost_Weight field and I need the result to be 0 if the RENEWAL_WEIGHT is 0.
I'm guessing 0 is a special value in this situation. This can be fixed by using CASE
Replace
dbo.Tops_Profile.H_WEIGHT - dbo.Tops_Profile.RENEWAL_WEIGHT AS Lost_Weight
With
CASE WHEN RENEWAL_WEIGHT = 0 THEN 0
ELSE dbo.Tops_Profile.H_WEIGHT - dbo.Tops_Profile.RENEWAL_WEIGHT
END AS Lost_Weight
Here is my statement:
SELECT
CASE
WHEN #UserRole = 1 THEN 1
ELSE 0
END AS [CanEdit],
F.FundingStreamName
FROM FundingStream AS F
LEFT JOIN Projects AS P ON P.FundingStream = F.FundingStreamID
WHERE ProjectNumber = #ProjectNumber
I noticed if FundingStreamID is null, the case statement will return nothing as well, how can I get the case statement to execute regardless if there is a funding stream or not? Thanks.
I think the problem is that your where clause is "undoing" your left outer join. Try moving the condition to the on clause:
SELECT (CASE WHEN #UserRole = 1 THEN 1
ELSE 0
END) AS [CanEdit],
F.FundingStreamName
FROM FundingStream F LEFT JOIN
Projects P
ON P.FundingStream = F.FundingStreamID AND
P.ProjectNumber = #ProjectNumber ;
Using #MicSim answer:
SELECT
CASE
WHEN #UserRole = 1 THEN 1
ELSE 0
END AS [CanEdit],
F.FundingStreamName
FROM FundingStream AS F
RIGHT JOIN Projects AS P ON P.FundingStream = F.FundingStreamID
WHERE ProjectNumber = #ProjectNumber
Thanks again for the help!
I will try to be as detailed as possible. Our corporate controller has asked me for some information regarding our suppliers. Here are the tables:
spp = supplier table, each supplier has one record, there are 5,222 records
ast = supplier account profile, there is a (M, 1) relationship between this table and spp, there are 8,950 records in this table. Each duplicate spp_id has a different atp_id which is a transaction profile.
crt = bank account information, a supplier may or may not have bank account info
xvd = table of checking tables, xvd.xcd_id is the field that holds the checking table id. Checking table 0007 is the table that contains the discount info.
Here is my script:
select spp.spp_id supp_num,
spp.spp_matchname supp_name,
case when spp.spp_ddcalculation = 0
then 'End of Month'
else
case when spp.spp_ddcalculation = 1
then 'Net'
else
case when spp.spp_ddcalculation = 2
then 'End of 10, 20, 30'
else
case when spp.spp_ddcalculation = 3
then 'End of 15 or 30'
else null
end
end
end
end calculation1,
convert(varchar(2), spp.spp_ddduration) + case when spp.spp_ddmd = 0
then ' Days'
else case when spp.spp_ddmd = 1
then ' Months'
else null
end
end duration1,
spp.spp_ddday stop_day1,
xvd.xvd_desc discount,
crt.crt_name bank,
case when ast.ast_ddcalculation = 0
then 'End of Month'
else
case when ast.ast_ddcalculation = 1
then 'Net'
else
case when ast.ast_ddcalculation = 2
then 'End of 10, 20, 30'
else case when ast.ast_ddcalculation = 3
then 'End of 15 or 30'
else null
end
end
end
end
calculation2,
convert(varchar(2), ast.ast_ddduration) + case when ast.ast_ddmd = 0
then ' Days'
else case when ast.ast_ddmd = 1
then ' Months'
else null
end
end
duration2,
ast.ast_ddday stop_day2
from spp left join ast on spp.spp_id = ast.spp_id
left join crt on ast.crt_id = crt.crt_id
inner join xvd on ast.cfd_id = xvd.xcv_id
where xvd.xcd_id = '0007'
and xvd.lng_id = 0
order by spp.spp_id
The problem is that there are 371 records in the ast table that have a non null cfd_id which is the field that relates to the discount in checking table 0007. When I run this I get 371 records, but I need all suppliers, even those with null discounts. I know the problem is a combination of my joins and the fact that there is not a null xcv_id in checking table 0007. Can anyone see anything glaring that I have overlooked?
To recap, there are 8,950 records in ast, but only 371 of them have a non null cfd_id. I need to grab all 8,950 records, I can't seem to extract the null discounts. I think I can probably pull everything into a temp table then grab the discounts, but am wondering if there is a way to do this in one select statement.
Thanks
Tony
Edit: The last line of my from statement seems to be the primary issue
inner join xvd on ast.cfd_id = xvd.xcv_id
There are no null xcv_id but there are null cfd_id. Is there another way to join those two tables, besides checking for equality?
Forgot to mention, we are on SQL Server 2008 R2.
Does this solve the problem ?
FROM spp
LEFT JOIN ast
ON spp.spp_id = ast.spp_id
LEFT JOIN crt
ON ast.crt_id = crt.crt_id
INNER JOIN xvd
ON xvd.xcv_id = ast.cfd_id
WHERE xvd.xcd_id = '0007'
AND xvd.lng_id = 0
I think you can just change your inner join to a left join:
from spp left join ast on spp.spp_id = ast.spp_id
left join crt on ast.crt_id = crt.crt_id
inner join xvd on ast.cfd_id = xvd.xcv_id
to
from spp left join ast on spp.spp_id = ast.spp_id
left join crt on ast.crt_id = crt.crt_id
left join xvd on ast.cfd_id = xvd.xcv_id
If you are saying that you want to select records where xvd.xcd_id is 0007 or null then change your where clause to this:
(xvd.xcd_id = '0007' OR xvd.xcd_id is null)
This sounds like a perfect use for views. Instead of trying to build one complex query, you could build a series of views that build upon one another filtering the data the way you want it... then apply the final query to the last view.
I am wondering if it is possible to specify multiple values in the then part of a case statement in T-SQL?
I have attached a chunk of code where I am using this to join in some tables in a query. I have included a comment in the snippet.
LEFT JOIN Business B ON v.BusID = B.BusID
LEFT JOIN BusinessTypeKey T ON B.BusinessTypeID = T.BusTypeID
LEFT JOIN Location L ON L.BusID = B.BusID
AND L.HeadQuarters = CASE
WHEN (SELECT COUNT(1) from Location L2
WHERE L2.BusID = B.BusID) = 1
THEN 1,0 -- Would like to specify either 1 or 0 here. I suppose I could also make it euqal to -> L.HeadQuarters but would like a better way to impose it
ELSE 1
END
This is a little ugly, but assuming HeadQuarters is not a decimal/numeric type and only integer values,
AND L.HeadQuarters BETWEEN CASE WHEN (SELECT COUNT...) = 1 THEN 0 ELSE 1 END AND 1;
You mean...?
LEFT JOIN whatever
ON...
CASE...WHEN...THEN...END = 1
OR
CASE...WHEN...THEN...END = 0