PeterBaileyUk
asked on
divide by zero error
Ive amended some code from an expert but I get a divide by zero error that makes sense but not sure how to stop that previously it was using int and just subtracting to get a variance ive changed to a percentage method instead the actualvariance field is now real data type
UPDATE dbo.TblCompareEvents
SET ActualVariance = ((CAST(isnull(prev,0) AS REAL) - CAST(change AS REAL))/(CAST(isnull(prev,0) AS REAL)*100))
WHERE TRY_CONVERT(REAL,Prev)IS NOT NULL
AND TRY_CONVERT(REAL,change) IS NOT NULL
One method would be to use the CASE statement to see if ISNULL(Prev, 0) equals zero. If it does, then substitute whatever value you want for ActualVariance when this situation occurs. Otherwise, you would perform your calculation.
Another option would be to use the WHERE clause to filter out data where ISNULL(Prev, 0) doesn't equal zero.
Another option would be to use the WHERE clause to filter out data where ISNULL(Prev, 0) doesn't equal zero.
What you want to do in the prev column is NULL?
Modifying it to zero it will give you the actual error so do you think it should be changed to one (1)?
Modifying it to zero it will give you the actual error so do you think it should be changed to one (1)?
UPDATE dbo.TblCompareEvents
SET ActualVariance = ((CAST(isnull(prev,0) AS REAL) - CAST(change AS REAL))/(CAST(isnull(prev,1) AS REAL)*100))
WHERE TRY_CONVERT(REAL,Prev)IS NOT NULL
AND TRY_CONVERT(REAL,change) IS NOT NULL
ASKER
in the previous iteration with just the subtraction I had tried to get it to put 0 instead of null. so it would do the calculation. the same applies albeit a different calculation BUT there is a high probability that I didnt understand it fully
ASKER
ive put to:
UPDATE dbo.TblCompareEvents
SET ActualVariance = ((CAST(prev AS REAL) - CAST(change AS REAL))/(CAST(prev AS REAL)*100))
WHERE TRY_CONVERT(REAL,Prev)IS NOT NULL
AND TRY_CONVERT(REAL,change) IS NOT NULL
That would work as long as Prev can never be zero.
ASKER
and ive added this before i run thie current question code so as to correct that issue
UPDATE dbo.TblCompareEvents
SET ActualVariance =0
WHERE Change not like '%[^0-9]%' and Change != '' and prev is null
You need to check if there's no prev with '0' on it:
SELECT *
FROM TblCompareEvents
WHERE prev='0'
If this query returns rows then you still have the issue.
ASKER
I still get the divide by zero although i guess that means the sql is actually ok
ASKER
yes vitor ok I will create an update to deal with that too now i get your earlier statement change it to 1
ASKER
I thought this might work but it gives conversion failed when converting nvarchar '39.8' to data type int
I was following on trying the case doesnt look right
I was following on trying the case doesnt look right
select PercDiff =
CASE prev
WHEN 0 THEN 0.01
WHEN '0' THEN 0.01
else (cast([ActualVariance] as int)/(CAST([prev] AS REAL)*100))
END
from TblCompareEvents
where ActualVariance is not null
39.8 is not integer. Is a decimal number so you need to convert it to float or real:
else (cast([ActualVariance] as float)/(CAST([prev] AS REAL)*100))
else (cast([ActualVariance] as float)/(CAST([prev] AS REAL)*100))
ASKER
ive taken the maths out and attached an excel file so DONT open if your on a phone please.
it was leading up to your idea from previous calculation
the actual variance is now populated its just that zero or data type clash
ee.xlsx
select prev, change, actualvariance
--, PercDiff =
--CASE prev
--WHEN 0 THEN 0.01
--WHEN '0' THEN 0.01
--else (cast([ActualVariance] AS REAL)/(CAST([prev] AS REAL)*100))
--END
from TblCompareEvents
where ActualVariance >0 and change<>'0'
it was leading up to your idea from previous calculation
UPDATE dbo.TblCompareEvents
SET PercentageDiff = (cast([ActualVariance] as real)/(CAST([prev] AS REAL)*100))
WHERE TRY_CONVERT(real,Prev)IS NOT NULL
AND TRY_CONVERT(real,change) IS NOT NULL
the actual variance is now populated its just that zero or data type clash
ee.xlsx
I didn't see the Excel file yet but if your ActualVariance field is already REAL you don't need to convert it:
[ActualVariance] /(CAST([prev] AS REAL)*100)
ASKER
yes i changed at one point.
its still flickering so its partially working i dont know where its trying to change 39.8 to an int
i tried this and its ran:
its still flickering so its partially working i dont know where its trying to change 39.8 to an int
i tried this and its ran:
UPDATE dbo.TblCompareEvents
SET PercentageDiff = [ActualVariance]/CAST([prev] AS REAL)*100
WHERE TRY_CONVERT(real,Prev)IS NOT NULL
AND TRY_CONVERT(real,change) IS NOT NULL
and TRY_CONVERT(real,Prev) <>0
ASKER
Those are the cases when prev = '0'. You can use a CASE statement for those cases:
UPDATE dbo.TblCompareEvents
SET PercentageDiff = CASE Prev
WHEN '0' THEN 0
ELSE [ActualVariance]/CAST([prev] AS REAL)*100
END
WHERE TRY_CONVERT(real,Prev)IS NOT NULL
AND TRY_CONVERT(real,change) IS NOT NULL
ASKER
now it went to the divide by zero again maybe it has another case
(3920 row(s) affected)
(82298 row(s) affected)
(82298 row(s) affected)
Msg 8134, Level 16, State 1, Procedure usp_UpdateActualVariance, Line 38 [Batch Start Line 3]
Divide by zero error encountered.
ASKER
UPDATE dbo.TblCompareEvents
SET PercentageDiff = CASE Prev
WHEN '0' THEN 0
WHEN 0 Then 0.1
ELSE [ActualVariance]/CAST([prev] AS REAL)*100
END
WHERE TRY_CONVERT(real,Prev)IS NOT NULL
AND TRY_CONVERT(real,change) IS NOT NULL
ASKER
i did this to discount the actual variance column and that processed so a zero is getting through on the prev
SET PercentageDiff = CASE Prev
WHEN '0' THEN 0
--[ActualVariance]/CAST([prev] AS REAL)*100
ELSE [ActualVariance]/6*100
END
ASKER
ive got it to do it but as a separate step
UPDATE dbo.TblCompareEvents
SET PercentageDiff = [ActualVariance]/CAST([prev] AS REAL)*100
WHERE TRY_CONVERT(real,Prev)IS NOT NULL
AND TRY_CONVERT(real,change) IS NOT NULL
AND TRY_CONVERT(real,Prev) <>0
UPDATE dbo.TblCompareEvents
SET PercentageDiff = [ActualVariance]/CAST([prev]+1 AS REAL)*100
where ActualVariance >0 and prev='0'
ASKER CERTIFIED SOLUTION
membership
This solution is only available to members.
To access this solution, you must be a member of Experts Exchange.
ASKER
thank you
Open in new window
So to avoid any fat-finger typos I'll let you take the above and alter your code accordingly.