Convert String column which has AM/PM to Timestamp in Impala - hive

I have a column which has values in string type like below:
31-Oct-2016 12:00 AM
31-May-2015 12:00 PM
I want to convert the above column values to timestamp in IMPALA. Tried with cast, to_timestamp and other ways , but it is either showing syntax error or Null as result.
Can you please suggest a solution
2nd Requirement
There is a column like below in string, I want it to be converted to timestamp alone.
31-Oct-2016 12:00
31-May-2015 12:00
please suggest a way, I'm new to Impala
Thanks in advance

You can use below code. Unfortunately, impala doesn't have am pm conversion capability, but you can use a little code to identify PM and add 12 hours to that to convert properly.
select
if (right('31-Oct-2016 02:09 PM',2)='PM',
to_timestamp('31-Oct-2016 02:09 PM','d-MMM-yyyy H:m') + interval 12 hours,
to_timestamp('31-Oct-2016 02:09 PM','d-MMM-yyyy H:m')
) ampm_timestamp
Second requirement -
Impala always expects 24hour hour format when it converts datetime. So, in your case for 12 AM scenario, we have to do some special logic like below.
First check if its 12 AM, then minus 12 hours, else check if its PM, then add 12 hours(which covers 12PM scenario) and finally if its any other AM, it simply converts to timestamp.
select
CASE WHEN right('31-Oct-2016 12:09 AM',2)='AM' AND RIGHT( SPLIT_PART('31-Oct-2016 12:09 AM',':',1),2)='12'
THEN to_timestamp('31-Oct-2016 12:09 AM','d-MMM-yyyy HH:mm') - interval 12 HOURS
ELSE CASE WHEN right('31-Oct-2016 12:09 AM',2)='PM'
THEN to_timestamp('31-Oct-2016 12:09 AM','d-MMM-yyyy HH:mm') + interval 12 HOURS
ELSE to_timestamp('31-Oct-2016 12:09 AM','d-MMM-yyyy HH:mm')
END END AMPM_TIMESTAMP

Related

Hours and minutes between 2 incorrectly formatted datetimes

So i have some timestamps in a DB and i want to get the hours and minutes difference from them
The problem is the timestamp portion is formatted incorrectly where the hour is always 12 and the minutes portion is actually the hours and the seconds is actually the minutes.
Example DB timestamp: 10/1/2020 12:08:52 AM
So in the above example the time is actually 8:52 AM not 12:08 AM
How can i convert this datetime to something i can use in order to calculate the difference in minutes and hours between these 2 oddly formatted timestamps?
My ideal end goal is something that displays the difference in the HH:MM format
EDIT: the timestamps in oracle actually look like below, and in this eaxmple the 12 means nothing and 18 is actually the hours.
Example of what I'm looking for:
01-OCT-20 12.18.44.000000000 AM - 01-OCT-20 12.12.42.000000000 AM
Output: 06:02 . so the timespan would be 6 hours and 2 minutes in this case.
Thanks,
You can turn your string to an Oracle date (resp timestamp) with to_date() (resp to_timestamp()):
to_timestamp(mystring, 'dd/mm/yyyy ss:hh12:mi am')
Then you can use date arithmetics to compute the difference. Substrating timestamps gives you an interval, which is pretty much what you seem to be looking for, so:
to_timestamp(mystring1, 'dd/mm/yyyy ss:hh12:mi am')
- to_timestamp(mystring2, 'dd/mm/yyyy ss:hh12:mi am')
as myinterval
Like so?
(my default date format is 'yyyy-mm-dd hh24:mi:ss' in Oracle ...)
WITH
indata(sdb) AS (
SELECT '10/1/2020 12:08:52 AM' FROM dual
UNION ALL SELECT '10/1/2020 12:08:52 PM' FROM dual
)
SELECT
TO_TIMESTAMP(sdb,'dd/mm/yyyy 12:hh:mi AM') AS ts
FROM indata;
-- out ts
-- out ---------------------
-- out 2020-01-10 08:52:00
-- out 2020-01-10 20:52:00

how can I subtract time from a date time field to adjust a date time field?

I currently have a datetime field in the following format: "2019-07-07 15:00:00 UTC". However, this date is an hour and 25 minutes ahead of what it should be. How can I subtract 1 hour and 25 minutes from this time in a new time field?
E.g., "I need 2019-07-07 15:00:00 UTC" to become "2019-07-07 13:35:00 UTC"
Language: SQL
Database: Pulling using Bigquery, which pulls from Google Cloud
The attached image shows the part of my SELECT statement I am working with. The first line is the date but in the database string form, the second line converts it to a date, and the third is trying to transform the date to subtract an hour and 25 mins.
Thanks in advance for the help!
You can try the below for subtracting Hours
SELECT TIMESTAMP_SUB(TIMESTAMP "2019-07-07 15:00:00 UTC", INTERVAL 1 HOUR)
Change your interval accordingly. In your case you can convert it into minutes and then use the MINUTE INTERVAL as shown below
SELECT TIMESTAMP_SUB(starts_at, INTERVAL 85 MINUTE)

What does TO_DATE('235959', 'HH24MISS') mean?

I came across a SQL query with below conditional clause
To_Char(CRTE_TMS, 'YYYYmmddHH24MISS') between To_Char (TO_DATE(:endDtTime,'YYYYmmddHH24MISS')-TO_DATE('235959', 'HH24MISS')) and :endDtTime
My high level understanding is that create time stamp should be between some time before end time and end time.
Not sure what does TO_DATE('235959', 'HH24MISS') mean.
If I run the below query on 5th Feb it returns 1st Feb
SELECT TO_DATE('235959', 'HH24MISS') FROM DUAl
Please help me understand what exactly this condition mean.
TO_DATE('235959', 'HH24MISS') creates a DATE value. Note, in Oracle data type DATE always contains date and time part.
If you don't provide any date value then Oracle defaults it to the first day of current months, so TO_DATE('235959', 'HH24MISS') returns "2018-02-01 23:59:59"
I don't think this condition makes sense:
To_Char(CRTE_TMS, 'YYYYmmddHH24MISS')
between To_Char (TO_DATE(:endDtTime,'YYYYmmddHH24MISS')-TO_DATE('235959', 'HH24MISS'))
and :endDtTime
First, you should compare DATE values, not strings.
I assume TO_DATE(:endDtTime,'YYYYmmddHH24MISS')-TO_DATE('235959', 'HH24MISS')) is wrong. I think you mean TO_DATE(:endDtTime,'YYYYmmddHH24MISS') - 1 + (1/24/60/60)
This will subtract 1 day plus 1 Second (1/24/60/60), i.e. subtract 23:59:59.
Another possibility would be TO_DATE(:endDtTime,'YYYYmmddHH24MISS') - INTERVAL '23:59:59' HOUR TO SECOND.
So, your condition could be
WHERE CRTE_TMS between TO_DATE(:endDtTime,'YYYYmmddHH24MISS') - 1 + (1/24/60/60) AND :endDtTime
This could probably be a comment instead of an answer.. Sorry do not have enough reputation.
HH24 is the 24 hour format of the hours.
235959 is 23 hours 59 minutes 59 second.
In a 12 hour format it means 11:59:59 PM.
The thing you are trying to do is converting date format into character and comparing it with other dates by converting them to character format using To_char. I do not suggest that.
The below would give the first of the month
SELECT TO_DATE('235959', 'HH24MISS') FROM DUAl;
I am not able to understand what you are trying to achieve here.
The below syntax gives in the character format which is the difference between two dates. for example 4 days and 10 hours.
To_Char (TO_DATE(:endDtTime,'YYYYmmddHH24MISS')-TO_DATE('235959', 'HH24MISS'))
and then you are trying to do a comparision like date between (4 days and 10 hours) and :endtime. This is incorrect.
You could use the below to convert to date format.
to_date('01012018 23:59:59','MMDDYYYY HH24:MI:SS')
select case when to_date('01012018 23:59:59','MMDDYYYY HH24:MI:SS') between :begindate and :enddate then 1
else null
from dual;

SQL Automatically converts 24 hour format time to 12 hour format

Time is visible on my table as follows
2017-09-15 16:30:00.000
And my Query is like this
Format(SlotStartTime,'dd/MM/yyyy hh:mi:ss') as SlotStartTime
And this returns time like this
15/09/2017 04:30:00
So the calculation gets wrong it should be 15/09/2017 04:30:00 PM or stay as it is in 24-hour format. How can I achieve this?
hh gives you 12 hour hours
HH gives you 24 hour hours
Also, mi is probably a typo, as it will return you a minute, followed by the letter i. Try this:
declare #datetime datetime = '2017-08-29 16:30:01'
select Format(#datetime,'dd/MM/yyyy HH:mm:ss') as SlotStartTime
You can find all valid datetime formatting characters here: https://learn.microsoft.com/en-us/dotnet/standard/base-types/custom-date-and-time-format-strings
hh is the code for 12 hour format. HH is the code for 24 hour format. It's similar to how mm (not mi) is for minutes and MM is for months.
You want:
FORMAT(SlotStartTime,'dd/MM/yyyy HH:mm:ss')
12 hour with the time period:
FORMAT(SlotStartTime,'dd/MM/yyyy hh:mm:ss tt')

T-SQL : convert(datetime) to include/exclude certain hours

Using date range to select values, but also need to use an hour range to determine if a record should be selected. The date ranges and time ranges are not necessarily associated.
game_time (between 6 am and 6 pm)
have tried straight between statement and datepart, but cannot get anything to capture what we need.
create table gametime(name varchar, start_time datetime, end_time datetime)
insert assorted name, start_times and end_times
Desired results
name start_time end_time
name1 8:00 AM 10:00 AM
name2 8:00 AM 11:30 AM
name3 4:00 PM 5:30 PM
name4 6:00 PM 9:00 PM
datetime is used is storage, but not needed in presentation.. only times are needed in presentation.
Selected games should only start between the hours of 6:00 AM and 6:00 PM.
Any and all suggestions and insight appreciated......
Using
LTRIM(RIGHT(CONVERT(VARCHAR(20), start_time, 100), 7))
to get the correct format for presentation,
but when I try to use
LTRIM(RIGHT(CONVERT(VARCHAR(20), start_time, 100), 7)) > 6
I get conversion errors.
I would use DATEPART rather than relying on converting to/comparing strings:
WHERE DATEPART(hour,start_time) BETWEEN 6 AND 18
Try CONVERT(VARCHAR(5),start_time,108) BETWEEN '06:00' AND '18:00'. Right now you're trying to compare a string to an integer.
Here's another way, provided you're on SQL Server 2008 or higher and have the TIME type available:
SELECT *
FROM gametime
WHERE CAST(start_time AS TIME) BETWEEN '06:00:00' and '18:00:00'
This can be a bit more flexible when your time range is not anchored to exact hours. It also is sarg-able -- i.e. it will use an index, where calling DATEPART will prevent that.