PostgreSQL UPDATE statement treats keyword as a column - sql

sorry for the noob question, just getting started with SQL and I have a problem that I could not resolve.
Basically, I created a table with "date of birth" column and chose wrong TYPE (integer), so every time I am trying to enter date of birth as "1998-01-04" it is just showing 1998. So, I decided to update the column to TEXT type.
Tried these queries
UPDATE users
SET date_of_birth = VARCHAR
It shows me error that there are no VARCHAR columns. Tried with as 'VARCHAR', still not working, tried as 'TEXT' and TEXT, still the same error.
What am I doing wrong?

Strings are as bad or worse than integers for this purpose. You want to use:
alter table alter column date_of_birth type date;
Note: If you have existing data in the column, you need to either use the using clause to convert it to a date. Or NULL it all out.

use this for your alter table statement
ALTER TABLE users
ALTER COLUMN date_of_birth TYPE VARCHAR(50);
I am not sure why you are storing date as varchar whereas you can store it as date, if you want to change that to date then use
ALTER TABLE users
ALTER COLUMN date_of_birth TYPE DATE;

Related

Converting all data in a Varchar column to a date format

I'm working on a table with a column, 'Expiry Date', as a varchar with all data formatted as DD/MM/YYYY.
The creator of the table has used the wrong type for this expiry date column and now the client needs to filter and show all records before and after the current date as the time. This means the type needs to be changed to date or datetime type to be able to use the CURDATE() function.
However, the current format of the values does not satisfy and wont allow the type to change unless the format is changed to YYYY-MM-DD (or similar).
Is there any way to mass format the values in this column and this column alone as there are thousands of entries and formatting one by one would be extremely time consuming.
Let me assume that you are using MySQL.
Perhaps the simplest method is to add a generated column that is a date:
alter table t add column expiry_date_date as
(str_to_date(expiry_date, '%d/%m/%Y'));
You can also fix the data:
update t
set expiry_date = str_to_date(expiry_date, '%d/%m/%Y');
This will implicitly convert the result of str_to_date() to a date, which will be in the YYYY-MM-DD format.
More importantly, you can then do:
alter table t modify column expiry_date date;
Here is a db<>fiddle.
You can do similar operations in other databases, but the exact code is a bit different.
What you need is an update on that column, but before doing it I suggest you to check if the result is what you want.
select replace(expiry_date, '/', '-') new_expiry_date
from table_name
If this returns the results you want you can run the following update:
update table_name
set expiry_date = replace(expiry_date, '/', '-')
Of course you will need to replace expiry_date and table_name with the names of your column and table.

SQL - Conversion failed when converting date and/or time from character string

I have 3 tables in the database that I'm working on. Out of 3, two of the tables have columns that include dates. When I checked the information schema of the columns I found that dates have the wrong data type. If you see the picture below, the highlighted columns should be stored as DATE data type.
So, I used the following query to change their data type from varchar to DATE:
ALTER TABLE [dbo].[Customer]
ALTER COLUMN DOB DATE;
ALTER TABLE [dbo].[Transactions]
ALTER COLUMN tran_date DATE;
The error that I get is:
Conversion failed when converting date and/or time from character string.
Please let me know how I can fix this error. Thanks!
What you can do is update the value using try_convert() first and then alter the column name. Note: This will set any invalid values to NULL.
update customer
set dob = try_convert(date, dob);
alter table customer alter column dbo date;
If you want to see the bad values, then before you change the table, run:
select c.*
from customer c
where try_convert(date, dob) is null and dob is not null;
You may have other ideas on how to fix the values.
You can't change from varchar to date or time or datetime by altering the column. Why? Because SQL Server does not know if the field contains '1/1/2020' or 'My dog is cute'. You will have to rebuild the table with the proper data types and then CAST() or CONVERT() the values to a true date time.
Underneath the hood, this makes more sense. A char/varchar uses one byte per character. nchar/nvarchar uses 2 bytes per character. A datetime is a number, not a character. This means you need a routine that changes this into the correct number. If you want to get deeper, the number is the number of ticks (nanoseconds) since midnight on January 1, 0001 in the Gregorian Calendar. More info.

ORA-01843: not a valid month error

I have a column in Oracle DB which is varchar2 data type. Typical value stored in this column is like 06/16/2015 02:14:18 AM.
I am trying to get all records wherein this column is having records after 1st August 2015.
select *
from MYTABLE
where to_date(substr(MYCOLUMN,1,10),'dd-mm-yyyy') > to_date('01-08-2015','dd-mm-yyyy');
But, I am getting ORA-01843. Where am I doing wrong?
Respect the format in your VARCHAR
....where to_date(substr(MYCOLUMN,1,10),'mm/dd/yyyy')
I have a column in Oracle DB which is varchar2 data type. Typical value stored in this column is like 06/16/2015 02:14:18 AM.
The first question is why do you store DATE as string? Using appropriate data type is one of the most important part of database design and performance.
Understand that DATE doesn't have the format you see, it is internally stored in 7 bytes which is Oracle's proprietary format. Storing date as a string to have a fixed format is not recommended.
I would suggest first fix the design so that you don't have to do this overhead activity while comparing dates. In the longer run it will help you.
1. Add a new column as DATE data type.
ALTER TABLE table_name
ADD new_column DATE;
2. Update the new column.
UPDATE table_name
SET new_column = TO_DATE(old_column, 'mm/dd/yyyy hh:mi:ss pm');
3. DROP the old column.
ALTER TABLE table_name
DROP COLUMN old_column;
4. Rename the new column to old column name.
ALTER TABLE table_name
RENAME COLUMN old_name to new_name;
Now, you could compare dates easily:
SELECT * FROM MYTABLE WHERE mycolumn > to_date('01-08-2015','dd-mm-yyyy');
This will also use any regular index on the date column.
From performance point of view:
If you don't fix it now, you will keep facing performance issues. Because the immediate fix of SUBSTR will not let you use any regular index, you need to create a function-based index.
If in your table all values like 06/16/2015 02:14:18 AM then you can use trunc(to_date(MYCOLUMN,'mm/dd/yyyy HH:mi:SS PM'),'dd') against to_date(substr(MYCOLUMN,1,10),'dd-mm-yyyy').

How to sort by varchar field containing a date in ascending order [duplicate]

This question already has answers here:
Comparing dates stored as varchar
(3 answers)
Closed 3 years ago.
In design time we have given [DOJInGovrService] field as varchar datatype.
now when we are trying order by this parameter(DOJInGovrService) in ascending order it is not giving the desired result.
I know it is datatype problem but I can't change the datatype now as data is already entered.
SELECT ED.class,
ED.CurrentOfficePlace,
ED.DOB,
ED.DOJInCurrentOff,
ED.DOJInGovrService,
ED.DOJInSamvarg,
ED.EmpName,
ED.HomePlace, ED.Qualification
FROM tbl_EmplyeesBiodata ED
ORDER BY DOJInGovrService asc
Date entered is in format dd-MM-yyyy (i.e. 28-08-2004).
please help me
This is just one of many reasons why you should Always use appropriate data types.
Even when you have data in the table, you can change the data type using an alter table ddl statement:
ALTER TABLE tableName
ALTER COLUMN ColumnName datetime2;
However, you should copy this table first and try the alter on the copy, so that if it messes up your data you will not risk anything.
If the alter is successful then do it on your live table. if not, you can go with a different approach, involving these stages:
rename the DOJInGovrService column to DOJInGovrService_old. use sp_RENAME.
Add a column DOJInGovrService with the correct datatype (datetime2), using alter table ddl stement.
Update the new DOJInGovrService column with the values in DOJInGovrService_old. you will probably need to use convert.
drop the DOJInGovrService_old column using the alter table ddl statement.
Try to convert it to datetime
select ED.class,ED.CurrentOfficePlace,ED.DOB,ED.DOJInCurrentOff,ED.DOJInGovrService,ED.DOJInSamvarg,ED.EmpName,ED.HomePlace,ED.Qualification
from tbl_EmplyeesBiodata ED
order by convert(date,DOJInGovrService,105) asc
This is only direct solution. The best way to do that is create new column with date type. The column will helps you to create query without cast or convert.

SQL invalid datatype time

I am trying to create a table in Oracle SQL*Plus and it won't take the datatype time, but has no problem taking the datatype date.
drop table order;
create table orders (
order_id char(4) not null,
order_date date,
order_time time, -- invalid datatype
cash_time char(3),
primary key(order_id)
);
That's weird... why is that? How can I fix it, or are there alternatives to using time?
In Oracle there is no datatype as TIME. You can use TIMESTAMP or DATE. So I think you need to change TIME to TIMESTAMP or DATE and things will work for you.
I think you are getting confused with this TIME datatype.
I quickly looked at the orcle datatype documentation and didn't see a time datatype and i think it's the problem.
why you don't use the date datatype as a single field instead of creating two field for date and time.