I have two parameters called START_DATE and END_DATE.
If the start date and end date are entered , i would like to use the TO_CHAR to convert to a different format and display ":start_date - :end_date" both in the format 'MON DD, YYYY')
However, if the parameters are not entered i would like to use the TO_CHAR function to display information for the previous month i.e ( MAR 01, 2017- MAR 31,2017).
Here's the code below. Can someone identify my error and assist?
SELECT DECODE (TO_CHAR(:START_DATE, 'MON DD, YYYY',(trunc(trunc(sysdate,'MONTH')-1,'MONTH'))),'MON DD, YYYY')
|| ' - ' || DECODE (TO_CHAR(:END_DATE, 'MON DD, YYYY',(trunc(sysdate,'MONTH')-1)'MON DD, YYYY') BILLPERIOD
How do i write this in sql using the decode function?
I highly recommend you use a CASE statement instead. More control, more readable, cleaner, etc. In my humble opinion of course.
SELECT
CASE
-- If one or both dates are NULL, revert to last month
WHEN start_date IS NULL OR end_date IS NULL THEN
to_char(trunc(trunc(sysdate,'MM')-1,'MM'), 'MON DD, YYYY') || ' - ' || to_char(trunc(sysdate,'MM')-1, 'MON DD, YYYY')
WHEN start_date IS NOT NULL AND end_date IS NOT NULL AND
(start_date < end_date) THEN
to_char(start_date, 'MON DD, YYYY') || ' - ' || to_char(end_date, 'MON DD, YYYY')
-- ** ALWAYS EXPECT THE UNEXPECTED! **
-- Like start_date >= end_date
ELSE '** DATE ERROR **'
END as billperiod
FROM dual;
EDIT: Added a check for start_date must be < end_date.
If you can use CASE in your project try:
SELECT
CASE START_DATE
WHEN NULL THEN TO_CHAR(PREVIOUS_DATE, 'MON DD, YYYY')
ELSE TO_CHAR(START_DATE, 'MON DD, YYYY')
END || ','
CASE END_DATE
WHEN NULL THEN TO_CHAR(PREVIOUS_DATE, 'MON DD, YYYY')
ELSE TO_CHAR(END_DATE, 'MON DD, YYYY')
END "Formated Date"
FROM BILLPERIOD;
Related
When I do...
Select TO_CHAR (date_field, 'Month DD, YYYY')
from...
I get the following:
July 01, 2011
April 01, 2011
January 01, 2011
Why are there extra spaces between my month and day? Why doesn't it just put them next to each other?
Why are there extra spaces between my month and day? Why does't it just put them next to each other?
So your output will be aligned.
If you don't want padding use the format modifier FM:
SELECT TO_CHAR (date_field, 'fmMonth DD, YYYY')
FROM ...;
Reference: Format Model Modifiers
if you use 'Month' in to_char it right pads to 9 characters; you have to use the abbreviated 'MON', or to_char then trim and concatenate it to avoid this. See, http://www.techonthenet.com/oracle/functions/to_char.php
select trim(to_char(date_field, 'month')) || ' ' || to_char(date_field,'dd, yyyy')
from ...
or
select to_char(date_field,'mon dd, yyyy')
from ...
You should use fm element to delete blank spaces.
SELECT TO_CHAR(sysdate, 'fmDAY DD "de" MONTH "de" YYYY') CURRENT_DATE
FROM dual;
SQL> -- original . . .
SQL> select
2 to_char( sysdate, 'Day "the" Ddth "of" Month, yyyy' ) dt
3 from dual;
DT
----------------------------------------
Friday the 13th of May , 2016
SQL>
SQL> -- collapse repeated spaces . . .
SQL> select
2 regexp_replace(
3 to_char( sysdate, 'Day "the" Ddth "of" Month, yyyy' ),
4 ' * *', ' ') datesp
5 from dual;
DATESP
----------------------------------------
Friday the 13th of May , 2016
SQL>
SQL> -- and space before commma . . .
SQL> select
2 regexp_replace(
3 to_char( sysdate, 'Day "the" Ddth "of" Month, yyyy' ),
4 ' *(,*) *', '\1 ') datesp
5 from dual;
DATESP
----------------------------------------
Friday the 13th of May, 2016
SQL>
SQL> -- space before punctuation . . .
SQL> select
2 regexp_replace(
3 to_char( sysdate, 'Day "the" Ddth "of" Month, yyyy' ),
4 ' *([.,/:;]*) *', '\1 ') datesp
5 from dual;
DATESP
----------------------------------------
Friday the 13th of May, 2016
try this:-
select to_char(to_date('01/10/2017','dd/mm/yyyy'),'fmMonth fmDD,YYYY') from dual;
select to_char(sysdate,'fmMonth fmDD,YYYY') from dual;
select to_char(sysdate, 'DD-fmMONTH-YYYY') "Date" from Dual;
The above query result will be as given below.
Date
01-APRIL-2019
i want to display in output as : today is wednesday
my code:
select to_char(sysdate,'today is' 'day' ) from dual ;
it is not working.
You need to include the raw text you want in the output in double quotes in the format specification:
select to_char(sysdate, '"today is" day') from dual ;
Output (as of 2020-03-04)
today is wednesday
Demo on dbfiddle
Use concat() or the concatenation operator || to prepend the 'today is ' string.
SELECT concat('today is ', to_char(sysdate, 'day'))
FROM dual;
or
SELECT 'today is ' || to_char(sysdate, 'day')
FROM dual;
I'm looking for some help in Oracle SQL. I need to query date and time in the where clause to find shift data based on current date. There are 3 shifts, 5am to 1pm, 1pm to 9pm and 9pm to 5am(next day morning. For example
SELECT 'T1' AS SHIFT, WORK_CENTER, SUM(CASE WHEN AQL='PASS' THEN 1 ELSE 0) END AS AQL_PASSED
FROM Z_INSPECTION_DEFECTS
WHERE DATE_TIME >= TO_DATE((SELECT CONCAT(TO_CHAR(CURRENT_DATE, ''DD-MON-YYYY''), '' 5:00:00 '') FROM DUAL) , ''DD-MON-YYYY HH:MI:SS '') AND
DATE_TIME < TO_DATE((SELECT CONCAT(TO_CHAR(CURRENT_DATE, ''DD-MON-YYYY''), '' 1:00:00 '') FROM DUAL) , ''DD-MON-YYYY HH:MI:SS '')
I do not get any results from this query. The date time field is a timestamp on local Los Angeles time.
The immediate problem is that you're looking dor times that are after 5am and before 1am, which logically means nothing matches - as no time can fulfil both at once. You can use 24-hour times instead:
WHERE DATE_TIME >= TO_DATE((SELECT CONCAT(TO_CHAR(CURRENT_DATE, ''DD-MON-YYYY''), '' 5:00:00 '') FROM DUAL) , ''DD-MON-YYYY HH24:MI:SS '') AND
DATE_TIME < TO_DATE((SELECT CONCAT(TO_CHAR(CURRENT_DATE, ''DD-MON-YYYY''), ''13:00:00 '') FROM DUAL) , ''DD-MON-YYYY HH24:MI:SS '')
But there are other ways to get those, e.g. just without the queries against dual:
WHERE DATE_TIME >= TO_DATE(TO_CHAR(CURRENT_DATE, ''DD-MON-YYYY'') || '' 5:00:00 '', ''DD-MON-YYYY HH24:MI:SS '') AND
DATE_TIME < TO_DATE(TO_CHAR(CURRENT_DATE, ''DD-MON-YYYY'') || ''13:00:00 '', ''DD-MON-YYYY HH24:MI:SS '')
or with truncation and date arithmetic:
WHERE DATE_TIME >= TRUNC(CURRENT_DATE) + (5/24) AND
DATE_TIME < TRUNC(CURRENT_DATE) + (13/24)
You really need to be getting those times in the target time zone though, e.g.:
WHERE DATE_TIME >= FROM_TZ(CAST(TRUNC(CURRENT_DATE) + (5/24) AS TIMESTAMP), ''America/Los_Angeles'') AND
DATE_TIME < FROM_TZ(CAST(TRUNC(CURRENT_DATE) + (13/24) AS TIMESTAMP), ''America/Los_Angeles'')
You need to be careful with current_date, which is in you current session time zone, and sysdate which is in the server time zone. If your session is UTC then current_date might not give you the day you expect.
(I've stuck with escaped single quotes as that is mostly what you have in the question, implying you're probably running this with dynamic SQL; whether you need to is another matter. If you're only doing that to provide the period offsets at runtime then that wouldn't need to be dynamic...)
You can see the generated times from those calculations with:
select FROM_TZ(CAST(TRUNC(CURRENT_DATE) + (5/24) AS TIMESTAMP), 'America/Los_Angeles'),
FROM_TZ(CAST(TRUNC(CURRENT_DATE) + (13/24) AS TIMESTAMP), 'America/Los_Angeles')
from dual;
FROM_TZ(CAST(TRUNC(CURRENT_DATE)+(5/24)ASTIMESTAM FROM_TZ(CAST(TRUNC(CURRENT_DATE)+(13/24)ASTIMESTA
------------------------------------------------- -------------------------------------------------
2018-10-22 05:00:00.000000000 AMERICA/LOS_ANGELES 2018-10-22 13:00:00.000000000 AMERICA/LOS_ANGELES
There is a column 'DateTime' that displays the Date and Time in 'YYYY/MM/DD HH24:MI:SS' format.
I need to display only the rows that has time in a particular range(2AM - 6AM) regardless of the particular date.
I have a code that only displays the time range(2AM - 6AM) for the particular day. I need to display the rows that falls in the past 7 days with the time range 2AM-6AM.
SELECT *
FROM <table_name >
WHERE DateTime BETWEEN TO_DATE (
TO_CHAR (TRUNC (SYSDATE), 'DD-MM-YYYY')
|| ' '
|| '02:00:00',
'DD-MM-YYYY HH24:MI:SS')
AND TO_DATE (
TO_CHAR (TRUNC (SYSDATE), 'DD-MM-YYYY')
|| ' '
|| '06:00:00',
'DD-MM-YYYY HH24:MI:SS')
ORDER BY 1 DESC
SELECT *
FROM your_table
WHERE TO_CHAR( DateTime, 'HH24MMSS' ) BETWEEN '020000' AND '060000'
AND DateTime >= TRUNC( SYSDATE ) - INTERVAL '7' DAY
AND DateTime < TRUNC( SYSDATE ) + INTERVAL '1' DAY
or
SELECT *
FROM your_table
WHERE DateTime BETWEEN TRUNC( DateTime ) + INTERVAL '2' HOUR
AND TRUNC( DateTime ) + INTERVAL '6' HOUR
AND DateTime >= TRUNC( SYSDATE ) - INTERVAL '7' DAY
AND DateTime < TRUNC( SYSDATE ) + INTERVAL '1' DAY
You need two conditions for that: one for the hour being between 02 and 05, and one for the day being in the last seven days:
SELECT *
FROM <table_name>
WHERE to_char(DateTime, 'HH') BETWEEN '02' and '05' AND
DateTime BETWEEN SYSDATE - 7 AND SYSDATE
ORDER BY 1 DESC
In this case, I think the easiest way is string comparison:
WHERE SUBSTR(DateTime, 12, 2) BETWEEN '02' and '05'
Note: Between is inclusive so this should get everything up to 05:59:59.
SELECT *
FROM <table_name >
WHERE DateTime BETWEEN TO_DATE (
TO_CHAR (TRUNC (SYSDATE)-7, 'DD-MM-YYYY')
|| ' '
|| '02:00:00',
'DD-MM-YYYY HH24:MI:SS')
AND TO_DATE (
TO_CHAR (TRUNC (SYSDATE), 'DD-MM-YYYY')
|| ' '
|| '06:00:00',
'DD-MM-YYYY HH24:MI:SS')
select * from table_name where to_char(datetime,'HH24')
between '2' and '6' and to_char(datetime,'dd-mon-yy')
between to_char(sysdate,'dd-mon-yy') and to_char(sysdate-7,'dd-mon-yy');
When I do...
Select TO_CHAR (date_field, 'Month DD, YYYY')
from...
I get the following:
July 01, 2011
April 01, 2011
January 01, 2011
Why are there extra spaces between my month and day? Why doesn't it just put them next to each other?
Why are there extra spaces between my month and day? Why does't it just put them next to each other?
So your output will be aligned.
If you don't want padding use the format modifier FM:
SELECT TO_CHAR (date_field, 'fmMonth DD, YYYY')
FROM ...;
Reference: Format Model Modifiers
if you use 'Month' in to_char it right pads to 9 characters; you have to use the abbreviated 'MON', or to_char then trim and concatenate it to avoid this. See, http://www.techonthenet.com/oracle/functions/to_char.php
select trim(to_char(date_field, 'month')) || ' ' || to_char(date_field,'dd, yyyy')
from ...
or
select to_char(date_field,'mon dd, yyyy')
from ...
You should use fm element to delete blank spaces.
SELECT TO_CHAR(sysdate, 'fmDAY DD "de" MONTH "de" YYYY') CURRENT_DATE
FROM dual;
SQL> -- original . . .
SQL> select
2 to_char( sysdate, 'Day "the" Ddth "of" Month, yyyy' ) dt
3 from dual;
DT
----------------------------------------
Friday the 13th of May , 2016
SQL>
SQL> -- collapse repeated spaces . . .
SQL> select
2 regexp_replace(
3 to_char( sysdate, 'Day "the" Ddth "of" Month, yyyy' ),
4 ' * *', ' ') datesp
5 from dual;
DATESP
----------------------------------------
Friday the 13th of May , 2016
SQL>
SQL> -- and space before commma . . .
SQL> select
2 regexp_replace(
3 to_char( sysdate, 'Day "the" Ddth "of" Month, yyyy' ),
4 ' *(,*) *', '\1 ') datesp
5 from dual;
DATESP
----------------------------------------
Friday the 13th of May, 2016
SQL>
SQL> -- space before punctuation . . .
SQL> select
2 regexp_replace(
3 to_char( sysdate, 'Day "the" Ddth "of" Month, yyyy' ),
4 ' *([.,/:;]*) *', '\1 ') datesp
5 from dual;
DATESP
----------------------------------------
Friday the 13th of May, 2016
try this:-
select to_char(to_date('01/10/2017','dd/mm/yyyy'),'fmMonth fmDD,YYYY') from dual;
select to_char(sysdate,'fmMonth fmDD,YYYY') from dual;
select to_char(sysdate, 'DD-fmMONTH-YYYY') "Date" from Dual;
The above query result will be as given below.
Date
01-APRIL-2019