how to insert text to date field in oracle - oracle

how to insert (text) time: 09:44:02 and date:11/09/2007 to date filed in Oracle ?
i have field Tdate (date) and Ttime (date) in oracle
thanks in advance

Since a date is a point in time you should really only use one field:
insert into your_table (dt)
values (to_date ('11/09/2007 09:44:02', 'dd/mm/yyyy hh24:mi:ss'));
Since your model contains two columns, you could use:
insert into your_table (Tdate, Ttime)
values (to_date('11/09/2007', 'dd/mm/yyyy'),
to_date ('09:44:02', 'hh24:mi:ss'));
Note however that by default your Ttime column will contain date information which may be false/irrelevant since you can not store only the time component:
SQL> select to_char(tdate), to_char(ttime) from your_table;
TO_CHAR(TDATE) TO_CHAR(TTIME)
------------------- -------------------
11/09/2007 00:00:00 01/08/2011 09:44:02

INSERT INTO <table>
(date_column)
VALUES
(TO_DATE(tdate||' '||ttime, 'DD/MM/YYYY HH24:MI:SS'))
/
If it is in PL/SQL
DECLARE
v_date_field DATE;
BEGIN
v_date_field := TO_DATE(tdate||' '||ttime, 'DD/MM/YYYY HH24:MI:SS');
--
INSERT INTO <table>
(date_column)
VALUES
(v_date_field);
END;
/
Don't forget to commit afterwards :-)

insert into tablename(tdate)
values(to_date('11/09/2007 09:44:02','dd/mm/yyyy hh24:mi:ss'))

Related

Oracle: Why do I have to use TO_DATE to pull my data?

When trying to filter on EXPIRE_DATE, it seems I have to use TO_DATE. Why do I have to use TO_DATE? The EXPIRE_DATE data type in the database is ALREADY set to date. Here is the code that works.
SELECT * FROM MY_TABLE
WHERE EXPIRE_DATE >= TO_DATE('2020/01/13','yyyy/mm/dd')
AND EXPIRE_DATE <= TO_DATE('2020/04/19','yyyy/mm/dd')
I tried to use BETWEEN without TO_DATE and just use my dates but I received an error.
To recap, even though the data type for this is ALREADY date, it seems I have to use TO_DATE to pull my data when I want to filter. Is there something I am missing? Here is my error when I try filter my data without using TO_DATE.
Apart from some good answers here, I would like to tell you that you do not need TO_DATE to pull the data from your table.
You need to_date or date literal to convert the normal string to date which can be compared to the column data in your table, As the date column must be compared with the date data type variable/constant.
To convert normal string to date, You can use the following:
TO_DATE('2020/01/13','yyyy/mm/dd')
DATE '2020-01-13'
I would not recommend using NLS_DATE_FORMAT just for creating the date.
You don't need to use TO_DATE, instead you can use a DATE literal:
SELECT *
FROM MY_TABLE
WHERE EXPIRE_DATE >= DATE '2020/01/13'
AND EXPIRE_DATE <= DATE '2020/04/19'
Or, if your NLS_DATE_FORMAT session parameter matches YYYY/MM/DD then you can insert the values as strings and rely on implicit string conversion (don't do this though):
ALTER SESSION SET NLS_DATE_FORMAT = 'YYYY/MM/DD';
SELECT *
FROM MY_TABLE
WHERE EXPIRE_DATE >= '2020/01/13'
AND EXPIRE_DATE <= '2020/04/19'
But it is not good practice to rely on the NLS_DATE_FORMAT as ANY user can change their own value at ANY time so your query can randomly fail when users start changing these values.
You can use BETWEEN:
Warning: it's better to use always TO_DATE function with proper format string and avoid implicit conversions that in some occasions produces strange behaviors in the results.
Warning: all columns of type DATE have always the hour-minute-second component.
if you forget this you may have fewer records in the result.
Example:
create table my_table
(id number,
expire_date date
);
Some data:
insert into my_table values ( 4,to_date('2011-06-17 10:07:18','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (12,to_date('2010-10-01 17:43:30','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (13,to_date('2011-07-30 08:38:34','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (21,to_date('2010-04-22 07:03:35','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (26,to_date('2011-03-26 02:07:57','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (35,to_date('2010-09-16 17:40:01','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (38,to_date('2011-11-05 17:27:45','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (44,to_date('2011-12-25 04:51:24','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (45,to_date('2011-11-05 03:08:51','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (54,to_date('2011-09-22 18:29:14','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (78,to_date('2010-03-12 20:23:21','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (79,to_date('2011-05-19 17:30:15','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (83,to_date('2011-11-15 10:04:58','yyyy-mm-dd hh24:mi:ss'));
insert into my_table values (96,to_date('2011-03-11 20:14:30','yyyy-mm-dd hh24:mi:ss'));
Set default date format to ISO-8601 international format:
alter session set nls_date_format='YYYY-MM-DD HH24:MI:SS';
Query using implicit conversion:
SELECT a.*
fROM my_table a
where expire_date between '2010-01-01 00:00:00'
and '2010-12-31 23:59:59';
Answer:
ID EXPIRE_DATE
12 2010-10-01 17:43:30
21 2010-04-22 07:03:35
35 2010-09-16 17:40:01
78 2010-03-12 20:23:21
but using US date format month-day-year:
SELECT a.*
fROM my_table a
where expire_date between '01/01/2010 00:00:00'
and '12/31/2010 23:59:59';
You got error:
ORA-01861: literal does not match format string
Change session date format to US format:
alter session set nls_date_format='MM-DD-YYYY HH24:MI:SS';
you can write dates in US format:
SELECT a.*
fROM my_table a
where expire_date between '01/01/2010 00:00:00'
and '12/31/2010 23:59:59';
And the answer is:
ID EXPIRE_DATE
---------- -------------------
12 10-01-2010 17:43:30
21 04-22-2010 07:03:35
35 09-16-2010 17:40:01
78 03-12-2010 20:23:21

checking a date column for blanks and if it is less than sysdate then replace it with sysdate

I have a date column( schedule date) datatype as varchar
ex:
3/22/2017
4/28/2017
5/3/2017
I need to check for nulls and if found any make it as sysdate
All dates <=sysdate should be converted to sysdate
so the above 3 records should become sysdates and i just want to capture the month
3/22/2017 should become 'May'
4/28/2017 should become 'May'
5/3/2017 should become 'May'
Thanks!
You can use a combination of to_date(), to_char() functions and a case statement. Something like this:
SELECT CASE when schedule IS NULL THEN to_char(SYSDATE, 'MONTH')
when (to_date(schedule, 'MM/DD/YYYY') < SYSDATE) THEN to_char(SYSDATE, 'MONTH')
else to_char(to_date(schedule, 'MM/DD/YYYY'), 'MONTH')
END AS SCHEDULE
FROM my_table;
The test:
CREATE TABLE MY_TABLE (SCHEDULE VARCHAR(10));
INSERT INTO MY_TABLE (SCHEDULE) VALUES ('3/22/2017');
INSERT INTO MY_TABLE (SCHEDULE) VALUES ('4/28/2017');
INSERT INTO MY_TABLE (SCHEDULE) VALUES ('5/3/2017');
INSERT INTO MY_TABLE (SCHEDULE) VALUES (NULL); -- test for null record
INSERT INTO MY_TABLE (SCHEDULE) VALUES ('6/1/2019'); -- test for future record (current May 2019)
COMMIT;
SELECT SCHEDULE as ORIGINAL_VALUE, CASE
when schedule IS NULL THEN to_char(SYSDATE, 'MONTH')
when (to_date(schedule, 'MM/DD/YYYY') < SYSDATE) THEN to_char(SYSDATE, 'MONTH')
else to_char(to_date(schedule, 'MM/DD/YYYY'), 'MONTH')
END as SCHEDULE_OUTPUT
FROM my_table;
DROP TABLE MY_TABLE;
Results:
ORIGINAL_VALUE SCHEDULE_OUTPUT
3/22/2017 MAY
4/28/2017 MAY
5/3/2017 MAY
MAY
6/1/2019 JUNE

Loop Insert Date a daily commit day to day timestamp ORACLE

im executing query in oracle. i need insert data everyday commit in looping like this :
DECLARE
start_date NUMBER;
end_date NUMBER;
business_date VARCHAR2 (8);
BEGIN
start_date := TO_NUMBER (TO_CHAR (TO_DATE ('2017-01-01', 'yyyy-MM-dd')));
end_date := TO_NUMBER (TO_CHAR (TO_DATE ('2018-01-01', 'yyyy-MM-dd')));
FOR cur_r IN start_date .. end_date
LOOP
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE TO_NUMBER (TO_CHAR (TO_DATE (datecreated, 'yyyy-MM-dd')))>=start_date+cur_r
AND TO_NUMBER (TO_CHAR (TO_DATE (datecreated, 'yyyy-MM-dd')))<=end_date;
COMMIT;
END LOOP;
END;
I dunt know error this script .. please help me .. btw i newbie in oracle sorry ..
As #boneist pointed out, your manipulation using numbers isn't going to work. You should keep the data type as it is and compare with values of the same data type.
Assuming you have a legitimate need to do this in a loop you could do something like this:
BEGIN
FOR r IN (
select date '2017-01-01' + level -1 as this_date
from dual
connect by level <= date '2018-01-01' - date '2017-01-01'
)
LOOP
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE datecreated >= r.this_date
AND datecreated < r.this_date + 1;
COMMIT;
END LOOP;
END;
/
Or if the data type is actually a timestamp rather than a date as suggested in a comment, something like:
BEGIN
FOR r IN (
select timestamp '2017-01-01 00:00:00'
+ (level -1) * interval '1' day as this_timestamp
from dual
connect by level <= extract(day from timestamp '2018-01-01 00:00:00'
- timestamp '2017-01-01 00:00:00')
)
LOOP
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE datecreated >= r.this_timestamp
AND datecreated < r.this_timestamp + interval '1' day;
COMMIT;
END LOOP;
END;
/
... though you might want to work on the condition for the connect-by query, e.g.
FOR r IN (
select timestamp '2017-01-01 00:00:00'
+ numtodsinterval(level -1, 'DAY') as this_timestamp
from dual
connect by timestamp '2017-01-01 00:00:00'
+ numtodsinterval(level -1, 'DAY') < timestamp '2018-01-01 00:00:00'
)
LOOP
...
or as #boneist suggested in a comment, with a simpler loop:
BEGIN
FOR num_days in 0..(date '2018-01-01' - date '2017-01-01' - 1)
LOOP
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE datecreated >= timestamp '2017-01-01 00:00:00'
+ numtodsinterval(num_days, 'DAY')
AND datecreated < timestamp '2017-01-01 00:00:00'
+ numtodsinterval(num_days + 1, 'DAY');
COMMIT;
END LOOP;
END;
/
The main problem with this approach is restartability. If there is an error part way through the loop you can't just re-run it, as you'd be inserting duplicates.
Multiple inserts and commits are also less efficient that a single insert, or even multiple inserts and a single commit. If you don't have enough undo space to allow a single transaction to do all the work you need you should be fixing the database configuration to allow that, rather than working around it and potentially compromising data integrity.
i need backup this table . and insert only 2 month in new table
That sounds like you need to partition the table by month and use partition swaps to shift old months from the live to the backup table, perhaps. Partitioning costs more but if you have those data volumes it may be justified.
Failing that you could consider renaming your current table to backup, recreating your original table, and just copying the two months' worth of data you want to keep back to that. But that's a one-off thing, you still have the ongoing problem of ageing records out of the main table and into backup. And it has its own issues with dependencies, constraints, etc.
You don't need any loop and you should skip all these TO_CHAR, TO_NUMBER, TO_DATE conversions. Try this:
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE datecreated BETWEEN DATE '2017-01-01' AND DATE '2018-01-01';
Perhaps datecreated has time values different to 00:00:00, in this case you should run
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE TRUNC(datecreated) BETWEEN DATE '2017-01-01' AND DATE '2018-01-01';
or in case datecreated is a VARCHAR2 data type rather than DATE run
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE TO_DATE(datecreated, 'YYYY-MM-DD') BETWEEN DATE '2017-01-01' AND DATE '2018-01-01';
Assuming your datecreated column is of data type DATE and you only want one copy of the rows of the table then you do not need PL/SQL:
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE datecreated BETWEEN DATE '2017-01-01' AND DATE '2018-01-01';
COMMIT;
You could use a DATE literal to set the start_date and end_date and use a loop like this.
DECLARE
start_date NUMBER;
end_date NUMBER;
BEGIN
start_date := DATE '2017-01-01';
end_date := DATE '2018-01-01';
FOR cur_r IN 0 .. (end_date - start_date)
LOOP
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE TRUNC (datecreated) = start_date + cur_r;
COMMIT;
END LOOP;
END;
Why wouldn't you do it using a simple INSERT, such as
INSERT INTO file_backup
SELECT *
FROM file_core
WHERE datecreated BETWEEN DATE '2017-01-01' AND DATE '2018-01-01';
If you're just practicing PL/SQL and loops, well, remove COMMIT out of the LOOP. Both START and END_DATE should be "converted" to a number using a proper format mask (i.e. yyyymmdd). FOR loop's index should go from 1 to a difference between END and START_DATE.
[EDITED, after reading MT0's comment]
[EDITED #2, after reading some more comments]
Bah, my code is rubbish, should've thought about what I'm doing. Basically, if I meant to write it properly, it would have looked like #Kaushik Nayak's, and there's really no point in doing it twice.

unable to insert into column (Oracle)

I am trying to insert into my date column of a table where my id column already has a value.I tried to use this query but it gave me error ORA00917 (missing coma)
insert into EXAMPLE
(TIME_1)
values(
(TO_DATE('2003/05/03 21:02:44', 'yyyy/mm/dd hh24:mi:ss'))
where ID=23);
Can anyone tell me where I did wrong?
Insert does not do updates.
update example
set time_1 = TO_DATE('2003/05/03 21:02:44', 'yyyy/mm/dd hh24:mi:ss')
where ID = 23;

Inserting timestamp in oracle timestamp column

I have a table in which there is a column with datatype TIMESTAMP(0)
When I insert a date into this column using
INSERT INTO TEST_TIMESTAMP VALUES(SYSDATE)
it inserts a date in the following example format
12-SEP-12 10.31.19.000000000 AM
I want to know how the below timestamp formats can be inserted in the table
12-SEP-12 10.31.19 and 12-SEP-12 10.31.19 AM
I tried specifying some formats using TO_CHAR while inserting SYSDATE into the table, but it didn't work.
Please suggest.
when you store a TIMESTAMP it will always store the data at maximum precision (with fractional seconds).
I think what you want to do is supply a format to display the date when you retrieve it from the database.
You can do this like so:
select to_char(timestampColumnName,'DD-MON-YY HH24:MI:SS') "Date" from test_timestamp
or
select to_char(timestampColumnName,'DD-MON-YY HH:MI:SS AM') "Date" from test_timestamp
You can return it very easy like:
SELECT to_char(sysdate,'DD-MON-YY HH24:MI:SS') FROM DUAL;
In your case use:
INSERT INTO TEST_TIMESTAMP(column_name) VALUES(to_char(sysdate,'DD-MON-YY HH24:MI:SS'));
You were missing the extra ().
INSERT INTO TEST_TIMESTAMP
VALUES (TO_TIMESTAMP('12-SEP-12 10.31.19', 'DD-MON-YY HH.MI.SS'));
INSERT INTO TEST_TIMESTAMP
VALUES (TO_TIMESTAMP('12-SEP-12 10.31.19 AM', 'DD-MON-YY HH.MI.SS AM'));
TO_CHAR(SYSDATE, 'DD/MM/YYYY HH24:MI:SS')
This for colum type insert over mode to_char.

Resources