How does one go abouts using a dynamically created field to be used within a DATE_SUB calculation?
I have this SQL below:
SELECT *,
CASE
WHEN `currentDate` IS NULL
THEN
`lastDate`
ELSE
`currentDate`
END AS `useDate`,
CASE
WHEN `type` = 'weekly'
THEN DATE_SUB(`useDate`, INTERVAL 1 WEEK)
END AS `nextDate`
FROM `aTable`
And this does not work, due to error '#1054 - Unknown column 'useDate' in 'field list''
The query works fine if I am using an actual field from the Select *, however won't accept the dynamically created field.
What would the proper way to work with this without having to do a 'case in case' query?
Did you try to use the CASE clause inside WHEN?
SELECT *,
CASE
WHEN `currentDate` IS NULL
THEN `lastDate`
ELSE `currentDate`
END AS `useDate`,
CASE
WHEN `type` = 'weekly'
THEN DATE_SUB(
CASE
WHEN `currentDate` IS NULL
THEN `lastDate`
ELSE `currentDate`
END AS `useDate`
, INTERVAL 1 WEEK)
END AS `nextDate`
FROM `aTable`
Related
I need to make a calculation by using a mysql query.
Here is my query.
SELECT book_name,
CASE WHEN CURDATE()<book_return THEN 0 ELSE DATEDIFF(CURDATE(),book_return) END AS DateDifference,
CASE WHEN DateDifference>0 THEN DateDifference*10 ELSE NULL) END AS TotalFines FROM tblIssuedBooks order by lastupdated DESC
I need to mutiply DateDifference column by 10 if the DateDIfference value is greater than zero.but when I execute this I am getting Unknown column 'DateDifference' in 'field list' as an error.
Can someone show me how to improve this?
You can't reuse an alias in a select which was defined in the same select. One workaround here uses a subquery:
SELECT book_name, DateDifference,
CASE WHEN DateDifference > 0 THEN DateDifference*10 END AS TotalFines
FROM
(
SELECT *, CASE WHEN CURDATE() < book_return
THEN 0
ELSE DATEDIFF(CURDATE(), book_return) END AS DateDifference
FROM tblIssuedBooks
) t
ORDER BY lastupdated DESC;
I have this particular salect query which acts strange:
(1)
select date_add(
CURRENT_DATE(),
INTERVAL 7*0+(CASE
WHEN tutoring_disponibilities.day < weekday(CURRENT_DATE())
THEN 7+(tutoring_disponibilities.day-weekday(CURRENT_DATE()))
ELSE tutoring_disponibilities.day-weekday(CURRENT_DATE())
END
)
DAY
) from tutoring_disponibilities where date_add(
CURRENT_DATE(),
INTERVAL 7*0+(CASE
WHEN tutoring_disponibilities.day < weekday(CURRENT_DATE())
THEN 7+(tutoring_disponibilities.day-weekday(CURRENT_DATE()))
ELSE tutoring_disponibilities.day-weekday(CURRENT_DATE())
END
)
DAY
) NOT IN (SELECT date(tutoring_sessions.startDate) from tutoring_sessions);
This returns nothing, but this (which is the first part of the where):
(2)
select date_add(
CURRENT_DATE(),
INTERVAL 7*0+(CASE
WHEN tutoring_disponibilities.day < weekday(CURRENT_DATE())
THEN 7+(tutoring_disponibilities.day-weekday(CURRENT_DATE()))
ELSE tutoring_disponibilities.day-weekday(CURRENT_DATE())
END
)
DAY
)
from tutoring_disponibilities;
returns:
'2020-03-30'
'2020-03-30'
'2020-03-31'
'2020-03-31'
'2020-03-25'
'2020-03-25'
and this part:
(3)
SELECT date(tutoring_sessions.startDate) from tutoring_sessions;
returns this:
'2020-01-29'
NULL
NULL
NULL
'2020-02-05'
'2020-02-05'
'2020-02-10'
'2020-02-11'
'2020-02-18'
'2020-02-17'
'2020-02-25'
'2020-02-24'
'2020-03-02'
'2020-03-09'
'2020-03-16'
'2020-03-23'
'2020-02-13'
'2020-02-13'
'2020-02-13'
'2020-02-24'
'2020-02-29'
'2020-03-14'
'2020-03-30'
'2020-03-30'
'2020-03-30'
We can see that '2020-03-30'is in the results of query (3) and also in the results of query (2), but the other results of query (2) are not present in the results of query (3).
So why query(1) doesn't return anything?
If you know a better way to express this code I would be glad of any kind of help!
My recommendation is not to use NOT IN with subqueries. The reason is that any NULL value in the subquery causes no rows to be returned.
I recommend NOT EXISTS. However, your expression is rather complicated, so the simplest fix to your query is:
NOT IN (SELECT date(tutoring_sessions.startDate)
FROM tutoring_sessions
WHERE tutoring_sessions.startDate IS NOT NULL
)
With an index on tutoring_sessions(startDate), the equivalent NOT EXISTS may also be noticeably faster.
I have a query like this to get status without adding fields.
SELECT * ,
IF(DATEDIFF(STR_TO_DATE(end_date, "%Y-%m-%d"), CURDATE())<=0,"End","Running") status
FROM agreements
the query is running but I want to add status if the end date is less than 3 days then the status will show "will be ended"
so there will be 3 statuses in the query, END, RUNNING, Will be END
You can use CASE ..WHEN statements; also your STR_TO_DATE(end, '%Y-%m-%d') usage is unnecessary because DATEDIFF() function considers date part only for the calculation:
SELECT * ,
CASE WHEN DATEDIFF(end_date, CURDATE()) <= 0 THEN 'End'
WHEN DATEDIFF(end_date, CURDATE()) < 3 THEN 'Will Be End'
ELSE 'Running'
END status
FROM agreements
In this query I use the CASE WHEN function to compare variables values in two different conditions. The problem is the number, because return a value = 1, but the correct result is NULL (20 is > of 8).
SELECT DISTINCT
case
when '20'>= '8' then null
when '20'< '8' then '1'
ELSE '0'
end checkValue
FROM DUAL;
How to resolve this problem?
The query run correctly if change 8 with 08. This solution is not applicable to because from variable arrive numers: 10 100 1000 units.
Thanks
I have change the field type from VARCHAR to DECIMAL and in this case work fine.
if you want compare string remember that string '20' < '8' so 'AB' is < 'C'
SELECT DISTINCT
case
when '20'>= '08' then null
when '20'< '08' then '1'
ELSE '0'
end checkValue
FROM DUAL;
otherwise if you want a number compare then you shoudl convert tne string as number
You need just cast strings to some numeric data type and then compare, for example
SELECT DISTINCT
case
when cast('20' as signed)>= cast('8' as signed) then null
when cast('20' as signed)< cast('8' as signed) then '1'
ELSE '0'
end checkValue
FROM DUAL;
Side note: DISTINCT no makes sense in this particular case
I have the following line of code that can either return one of 2 conditions ('Expired','Active'). I needed to use DATEDIFF to figure out the dates I needed.
However, now I need to alter this code so that I can add a sort of else if condition if neither of the 2 conditions are met and result to 'Unknown'.
I have this so far:
SELECT
IF(DATEDIFF(#endDate:=ADDDATE(h.StartDate,Interval h.NumMonth Month),NOW())<0,'Expired',
IF(DATEDIFF(#endDate,NOW())<120,'Expires in 120 days or less','Active')) AS bActive
FROM ...
So, for now, I have Expired, Active but I also want to include else 'Unknown' to be included as option. How would I alter this logic? Do I need to use ELSEIF or CASE? What should I use?
Use case instead of if. First, case is ANSI standard, so it works across databases. Second, it handles multiple conditions better. I think your logic is:
SELECT (CASE WHEN DATEDIFF(ADDDATE(h.StartDate, Interval h.NumMonth Month), NOW()) < 0
THEN 'Expired'
WHEN DATEDIFF(ADDDATE(h.StartDate, Interval h.NumMonth Month), NOW()) < 120
THEN 'Expires in 120 days or less'
ELSE 'Active'
END) AS bActive