how to replace date in postgres with a static number - sql

I am writing a Postgres procedure and I want to replace only date part of date with some static no.
eg:-
varDate Date default '2018-05-21';
Say I want to make this date as '2018-05-08';
Can anyone tell how to achieve this.
Till now what i have tried is this
varDate := varDate - interval '1 day' * 21 + interval '1 day' * 8;
The above expression gives me proper results. But is there any shortcut to change only the date part of the date.

As far as I understand you want to change the day of the month to 8.
One way to do this is to "truncate" the date to the start of the month, then add 8 days:
vardate := date_trunc('month', vardate)::date + 8;
date_trunc returns a timestamp that's why the cast ::date is needed.
Another option is to "build" a date based on the existing date:
vardate := make_date(extract(year from vardate)::int, extract(month from vardate)::int, 8);

Another option is to add a number of days to the date so you land on the 8th day:
select vardate::date + (8 - extract(day from vardate) * interval '1 day'

Related

Incrementing Date - SQL(Snowflake)

I want to Increment/Decrement the Year , Day , Month by pulling in the Current Date in Snowflake in a single query ?
For e.g.
Suppose Current System Date - 04082021 I want to make it 05092022. I have tried the dateadd function but I suppose it allows only one part i.e. either year or month or day to be incremented at once.
Is it Possible ? If Not, What are the other alternatives ?
If you want to useDATEADD function, here is the code:
SELECT DATEADD(YEAR,+1,DATEADD(MONTH,+1,DATEADD(DAY,+1,CURRENT_DATE())));
returns 2022-09-05 from 2021-08-04
If you want to keep your format, Please use following code
SELECT TO_CHAR(DATEADD(YEAR,+1,DATEADD(MONTH,+1,DATEADD(DAY,+1,CURRENT_DATE()))),'DDMMYYYY');
I would do the arithmetic in thee parts:
select current_date + interval '1 year' + interval '1 month' + interval '1 day'
You can also use:
select current_date + interval '1 year, 1 month, 1 day'

PostgreSQL convert month string to start and end dates of month

Is it possible to convert e.g. string "201701" to dates '2017-01-01' and '2017-01-31' in PostgreSQL?
So for:
"201701" get '2017-01-01' and '2017-01-31'
"201702" get '2017-02-01' and '2017-02-28'
"201703" get '2017-03-01' and '2017-02-31'
etc
You may use the TO_DATE function, and append the day component using string concatenation, something like this:
SELECT
TO_DATE('201702' || '01', 'YYYYMMDD') AS first,
(TO_DATE('201702' || '01', 'YYYYMMDD') + INTERVAL '1 month') -
INTERVAL '1 day' AS last;
The above trick just adds 01 to form the first of the month. For the last day of the same month, it first adds one month to the first, to get the first of the next month, then rolls back one day to get the last of the current month.
Demo
The above answer by Tim Biegeleisen works, but here's an alternative.
The to_date() function converts a string literal to a date value.
sample usage is : to_date(text,format);
SELECT to_date('201701','YYYYMMDD');
(EDITED)
You can also use date_trunc which is a part of PostgreSQL. It does the same as the above one.
select date_trunc('month', current_date) , date_trunc('month', CURRENT_DATE) + interval '1 month - 1 day';
Code Example Live Demo

How to get the last day of month in postgres?

How to find the last day os the month in postgres?
I have a date columns stored as numeric(18) in the format(YYYYMMDD)
I am trying it to make it date using
to_date("act_dt",'YYYYMMDD') AS "act date"
then find the last day of this date:
like this:
(select (date_trunc('MONTH',to_date("act_dt",'YYYYMMDD')) + INTERVAL '1 MONTH - 1 day')::date)
but it gives me this error:
ERROR: Interval values with month or year parts are not supported
Detail:
-----------------------------------------------
error: Interval values with month or year parts are not supported
code: 8001
context: interval months: "1"
query: 673376
location: cg_constmanager.cpp:145
process: padbmaster [pid=20937]
-----------------------------------------------
Any help?
Postgres version:
PostgreSQL 8.0.2 on i686-pc-linux-gnu, compiled by GCC gcc (GCC) 3.4.2 20041017 (Red Hat 3.4.2-6.fc3), Redshift 1.0.874
For anybody coming to this question looking for the Postgres way to do this (not using Redshift), here's how you'd do it:
SELECT (date_trunc('month', '2017-01-05'::date) + interval '1 month' - interval '1 day')::date
AS end_of_month;
Replacing the '2017-01-05' with whatever date you want to use. You can make this into a function like this:
create function end_of_month(date)
returns date as
$$
select (date_trunc('month', $1) + interval '1 month' - interval '1 day')::date;
$$ language 'sql'
immutable strict;
EDIT Postgres 11+
Pulling this out of the comments from #Gabriel, you can now combine interval expressions in one interval (which makes things a little shorter):
select (date_trunc('month', now()) + interval '1 month - 1 day')::date as end_of_month;
-- +--------------+
-- | end_of_month |
-- +--------------+
-- | 2021-11-30 |
-- +--------------+
-- (1 row)
If you're using Amazon AWS Redshift then you can use Redshift's LAST_DAY function. While Redshift is based on PostgreSQL, the LAST_DAY function is not available in PostgreSQL, for a solution for PostgreSQL see #wspurgin's answer.
https://docs.aws.amazon.com/redshift/latest/dg/r_LAST_DAY.html
LAST_DAY( { date | timestamp } )
LAST_DAY returns the date of the last day of the month that contains date. The return type is always DATE, regardless of the data type of the date argument.
For example:
SELECT LAST_DAY( TO_DATE( act_date, 'YYYYMMDD' ) )
Okay, so you've got a numeric(18) column containing numbers like 20150118. You can convert that to a date like:
to_date(your_date_column::text, 'YYYYMMDD')
From a date, you can grab the last day of the month like:
(date_trunc('month', your_date_column) +
interval '1 month' - interval '1 day')::date;
Combined, you'd get:
select (date_trunc('month', to_date(act_dt::text, 'YYYYMMDD')) +
interval '1 month' - interval '1 day')::date
from YourTable;
Example at SQL Fiddle.
date_trunc('month',current_date) + interval '1 month' - interval '1 day'
Truncating any date or timestamp to the month level will give you the first of the month containing that date. Adding a month gives you the first of the following month. Then, removing a day will give you the date of the last day of the month of the provided date.
For future searches, Redshift does not accept INTERVAL '1 month'. Instead use dateadd(month, 1, date) as documented here.
To get the end of the month use: DATEADD(DAY, -1, (DATE_TRUNC('month', DATEADD(MONTH, 1, date))))
select to_char(date_trunc('month', now() + '01 Months'::interval) - '01 Days'::interval, 'YYYYmmDD'::text)::numeric as end_period_n

how do I convert mmyy to last day of month in netezza

One of my column needs to be transformed into a date field. It contains a value that gives the YYMM and it should be translated into the last day of that month:
For example, 1312 should become 12/31/2013.
I have tried various last_day, to_char functions but not able to convert 1312 in a date format. Please help !!
Netezza is based on Postgres, so maybe the Postgres method will work. Here is Postgres code that works (see here):
select to_date('1312'||'01', 'YYMMDD') + interval '1 month' - interval '1 day'
I would first convert the number to a date, then add 1 month and subtract 1 day.
select add_months(to_date(1312, 'yymm'), 1) - 1 as the_date

MySQL date_add() how to use month into this?

Hallo all, i have this SQL
SELECT DATE_ADD( '2009-'+ MONTH( NOW() ) +'-01' , INTERVAL -1 MONTH );
i can't get it to work, what i make wrong here?
tanks for help.
SELECT CONCAT_WS('-', '2009', MONTH(NOW()), '01') - INTERVAL 1 MONTH
It's the concatenation of the date that doesn't work. It converts the strings to numbers, so you get 2009+11+-1 = 2019, which then fails to convert to a date.
Instead of concatenating a date from strings, you can use the last_day function to get the last day of the current month, add one day to get to the next day of the next month, then subtract two months to get to the first day of the previous month:
select last_day(now()) + interval 1 day - interval 2 month;
Plus is an arithmetical operator, you have to use concat.
SELECT DATE_ADD( concat('2009-',MONTH(NOW()),'-01') , INTERVAL -1 MONTH )
or better
select date(now()) - interval day(NOW())-1 day - interval 1 month;
(this will also work in 2010)