How to skip days in mysql? - mysql

I am creating a report where I have to show last 7 days data and previous 7 days data. But I can fetch last 7 days data but for previous 7 days I don't know how to write the sql!
Suppose today is 14th March. I am fetching data from database for last 7 days which is 8th March to 14th March is,
WHERE my_date >= DATE_ADD(NOW(), INTERVAL -7 DAY)
But how to write the sql for previous 7 days? Which is 1st March to 7th March.
I have tried this,
WHERE my_date BETWEEN DATE_SUB(NOW(),INTERVAL 7 DAY) and NOW()
I don't think it's working! How am I going to get data for 1st March to 7th March and skip 8th March to 14th March?

Have you try this :
WHERE my_date BETWEEN DATE_SUB(NOW(),INTERVAL 14 DAY) and DATE_SUB(NOW(),INTERVAL 7 DAY)

Related

MySQL get next day & time combination

Using MySQL, how do I find the next weekday/time combination after a given datetime?
For example, how do I select the next Sunday at 10AM given an input date of Tuesday 12 August 2014 6PM - which should return: Sunday 17 August 10AM?
SELECT DATE_ADD(#input_date, INTERVAL (8 - DAYOFWEEK(#input_date)) DAY) AS next_sunday
From: http://www.gizmola.com/blog/archives/99-finding-next-monday-using-mysql-dates.html
SELECT DATE_ADD('2014-08-12', INTERVAL 5 DAY) as NEXTSUNDAY;

Getting the last month's dates in mysql

I need to get the last month's dates from 1st to current date. Suppose if today's date is March 25th, I need to get the dates from 1st to 25th of february. Suppose if today's date is March 30th, I need to get the dates from 1st to 28/29th Feb, whatever the maximum final date is available. I have searched a lot to get that, but no luck. Can someone please help me how to get this special case done? I am able to do it on another database, but I want to do this on mysql.
Basically what I did for other database is this --> date between date(to_char(date(add_months(DATE(sysdate) ,-1)),'YYYY-MM-01 00:00:00')) and date(add_months(DATE(sysdate) ,-1))
This should do what you want:
WHERE d BETWEEN DATE_FORMAT(DATE_SUB(NOW(), INTERVAL 1 MONTH), '%Y-%m-01')
AND DATE_SUB(CURDATE(), INTERVAL 1 MONTH);
You can use DATE(DATE_SUB(NOW(), INTERVAL 1 MONTH)). This will automatically limit the result to the last day of the month, so if today's date is March 30th, this will return Feb 28th.

MYSQL Interval - Same day of the week one year in the future

Does anyone have a snippet of MYSQL code that will give me the new datetime of a day one year in the future that is the same day of the week?
SELECT new_day = ADDDATE(new_day,INTERVAL 364 DAY) FROM my_table
Works on non-leap years. Any ideas how to deal best with leap years?
Given that a normal year is 52 weeks and 1 day long and a leap year is 52 weeks and 2 days long, your new date will be one or two days earlier in the year than it was in the old year. For any date after New Year's Day in a regular year, or any date after the 2nd of January in a leap year, adding 52 week or 364 days gives you a date in the next year that is on the same day of the week and occurs 1 or 2 days earlier in the month (or at the end of the prior month).
That leaves you with the problem of what to do with the first two days of the year. Presumably 'next year' is crucial, so the simple answer that 2013-12-31 is 52 weeks later than 2013-01-01 is not OK. In this case, you have to write a conditional expression, spelled CASE in SQL.
SELECT CASE WHEN YEAR(DATEADD(ref_date, INTERVAL 364 DAY)) = YEAR(ref_date)
THEN DATEADD(ref_date, INTERVAL 371 DAY)
ELSE DATEADD(ref_date, INTERVAL 364 DAY)
END
FROM ...wherever...
how do you wish it to deal with leap years? either save month and date and compare if 364 or 371 are closest to first day, and pick regardingly, or do nothing and face inaccuracy after a couple of years.
*saved_date* is the very first date before created new dates based on it
*passed_years* is increasing for every new since the first
date_add(last_date, INTERVAL (case when datediff(date_add(saved_date, INTERVAL passed_years YEAR), date_add(last_date, INTERVAL 371 DAY)) <= 3 then 371 else 364 end)) DAY)
The idea of this is to either fetch 52 or 53 weeks of the next year. leap years doesn't affect weekdays, but they "contribute" to an already existing problem; the date gets lower for each passing year if you only add 52 weeks each year without above solution.
Why not simply
CURDATE() + INTERVAL 52 WEEK`
Sure, it will be 1 or 2 days earlier in the 'calendar'.
mysql> SELECT NOW(), CURDATE() + INTERVAL 52 WEEK;
+---------------------+------------------------------+
| NOW() | CURDATE() + INTERVAL 52 WEEK |
+---------------------+------------------------------+
| 2017-09-05 15:50:46 | 2018-09-04 |
+---------------------+------------------------------+
If you need it to be 'later', then use 53.

Get ToDate , FromDate from Week Number in MySQL

I easily get Week Number using MySql Week function like this WEEK(SYSDATE())
I just wanted to know how to get from and to date using week number in MySQL.
Result required:
Week No From date To date
Week 25 June 18, 2012 June 24, 2012
This works great for this kind of job:
SELECT
ADDDATE(CURDATE(), INTERVAL 1-DAYOFWEEK(CURDATE()) DAY) _From,
ADDDATE(CURDATE(), INTERVAL 7-DAYOFWEEK(CURDATE()) DAY) _To;
Beware that first day of week here is Sunday. It may depends on your country convention ;)

Calculating last years current week starting date and ending date

I am trying to calculate last years starting day of the "current week NOW()" and the ending day of that week. Along with this I am needing an offset as sometimes the Starting day of the week may not be Sunday or Monday, but even possibly a Thursday.
If a week starts on a Tuesday for instance it will end on a Monday. Given this if the current day is Thursday I need to be able to calculate the Tuesday and Monday.
I understand how to get last years current day.
SELECT DATE_SUB(NOW(), INTERVAL 1 YEAR);
But with the offset requirement here I am having issues calculating the starting day of that week and ending day of that week. Which needs to be in a "date format."
* Working to clarify this more... My example was off...
***Edit
For the sake of argument (and example), let's say that today is Jan 23, 2012. My task is to accept that date and return the start and end dates for that week of the previous year.
My assumptions are:
1) a week is defined as having a thursday (ie 2011 week 1 is 1/2 - 1/8)
2) start of week is Sunday
According to the week numbering scheme as I understand it with the above assumptions, week 1 is the first week with a Thursday. That means, Jan 23 falls within week 4 in 2012. This is confirmed with WEEK('2012-01-04') = 4. My target thus is to select the start and end dates of week 4 of the previous year. In 2011, the results would be Jan 23 - Jan 29.
Complicating this further is then to adjust the start of the week (modify assumption 2). Continue to use WK4... 2011, Jan 23 - Jan 29, Sun - Sat, If I say the start of the week is Monday, then I would adjusting the dates by one... giving Jan 24 - Jan 30. Tues adjusts by 2... Jan 25 - Jan 31, etc.
The approach is two steps:
1) calculate the start and end of the true year week
2) slide it into the "future" by whatever the start day would be
While the sliding into the future may or may not be correct, it would at least yield consistent results based on the conventional understanding of what "week 4" means.
Unfortunately PHP is not necessarily an option here. We need this to be ran inside of a SELECT START_WEEK, END_WEEK;
Any advice or help towards solving this query would be much helpful.
Thanks
Well, ISO 8601 assumes:
a week is defined as having a Thu
the start of a week is Mon
Jan 23 falls within week 4 of 2012 which you can confirm with
SELECT WEEK('2012-01-23', 3) = 4;
Week 4 of 2012 is Jan 23 to Jan 29 which you can confirm with the calendar at whatweekisit.com. As a query, you can calculate with:
SELECT
WEEK('2012-01-23', 3) AS weekNumber,
DATE_SUB('2012-01-23', INTERVAL DAYOFWEEK('2012-01-23') - 2 DAY) AS startOfWeek,
DATE_ADD('2012-01-23', INTERVAL 8 - DAYOFWEEK('2012-01-23') DAY) as endOfWeek;
Week 4 of 2011 is Jan 24 to Jan 30 (also confirmable by calendar). It is true that same date may not fall within the current week number and last year's week, but I don't suspect they would be wildly different.
SELECT
IF (WEEK('2012-01-23', 3) = WEEK(DATE_SUB('2012-01-23', INTERVAL 1 YEAR), 3),
DATE_SUB(DATE_SUB('2012-01-23', INTERVAL 1 YEAR), INTERVAL DAYOFWEEK(DATE_SUB('2012-01-23', INTERVAL 1 YEAR)) - 2 DAY),
DATE_SUB(DATE_SUB(DATE_ADD('2012-01-23', INTERVAL 6 DAY), INTERVAL 1 YEAR), INTERVAL DAYOFWEEK(DATE_SUB(DATE_ADD('2012-01-23', INTERVAL 6 DAY), INTERVAL 1 YEAR)) - 2 DAY)) AS datetimeStart;
Notice that I'm always representing the calculations verbatim in several places (e.g. DATE_SUB('2012-01-23', INTERVAL 1 YEAR) of Jan 32 2011); if you're doing this within a stored procedure or UDF you can probably use variables to make it more concise/readable/maintainable.
Now that the start and end of the target year week has been identified, you can simply apply your offset. Given $weekDayStart is 0 - 6 (Sun - Sat):
SELECT
DATE_ADD(
IF (WEEK('2012-01-23', 3) = WEEK(DATE_SUB('2012-01-23', INTERVAL 1 YEAR), 3),
DATE_SUB(DATE_SUB('2012-01-23', INTERVAL 1 YEAR), INTERVAL DAYOFWEEK(DATE_SUB('2012-01-23', INTERVAL 1 YEAR)) - 2 DAY),
DATE_SUB(DATE_SUB(DATE_ADD('2012-01-23', INTERVAL 6 DAY), INTERVAL 1 YEAR), INTERVAL DAYOFWEEK(DATE_SUB(DATE_ADD('2012-01-23', INTERVAL 6 DAY), INTERVAL 1 YEAR)) - 2 DAY)),
INTERVAL $weekDayStart - 1 DAY) AS datetimeStart,
DATE_ADD(
IF (WEEK('2012-01-23', 3) = WEEK(DATE_SUB('2012-01-23', INTERVAL 1 YEAR), 3),
DATE_SUB(DATE_SUB('2012-01-23', INTERVAL 1 YEAR), INTERVAL DAYOFWEEK(DATE_SUB('2012-01-23', INTERVAL 1 YEAR)) - 2 DAY),
DATE_SUB(DATE_SUB(DATE_ADD('2012-01-23', INTERVAL 6 DAY), INTERVAL 1 YEAR), INTERVAL DAYOFWEEK(DATE_SUB(DATE_ADD('2012-01-23', INTERVAL 6 DAY), INTERVAL 1 YEAR)) - 2 DAY)),
INTERVAL $weekDayStart + 5 DAY) AS datetimeEnd;
So, working it through with the input of 2012-01-23 and start day of Thurs would yield:
Jan 23 2012 = week 4
week 4 of 2011 = 1/24-1/30
Offset Thu - Mon (4 - 1) is +3 which moves window to Jan 27 - Feb 2 2011
Found it... Had to read up on the issue a little more.
This ended up being 7 different queries.
My Base Query:
Sunday Start Day of Week
SELECT
DATE_SUB(
DATE_ADD(
STR_TO_DATE( CONCAT( YEAR('2012-01-04')-1, '-01-01' ), '%Y-%m-%d'), #Get last year starting date.
INTERVAL WEEK('2012-01-04') WEEK),
INTERVAL 6 DAY) START_DAY_OF_WEEK,
DATE_ADD(
STR_TO_DATE( CONCAT( YEAR('2012-01-04')-1, '-01-01' ), '%Y-%m-%d'),
INTERVAL WEEK('2012-01-04') WEEK) END_DAY_OF_WEEK;
This gets me Week 1 of 2011. Starting of that week is 1/2 and ending on 1/8.
Now if my week starts on a different day I add in an offset...
Tuesday Start Day of Week
SELECT
DATE_SUB(
DATE_ADD(
STR_TO_DATE( CONCAT( YEAR('2012-01-04')-1, '-01-01' ), '%Y-%m-%d'), #Get last year starting date.
INTERVAL WEEK('2012-01-04') WEEK),
INTERVAL 4 DAY) START_DAY_OF_WEEK,
DATE_ADD(
DATE_ADD(
STR_TO_DATE( CONCAT( YEAR('2012-01-04')-1, '-01-01' ), '%Y-%m-%d'), #Get last year starting date.
INTERVAL WEEK('2012-01-04') WEEK),
INTERVAL 2 DAY) END_DAY_OF_WEEK;
This will give me 1/4 start day of week and ending on 1/10.
To get the other days of the week is relatively simple:
Sunday (First Query...)
Monday -5 start day +1 end day.
Tuesday -4 start day +2 end day.
Wednesday -3 start day +3 end day.
Thursday -2 start day -4 end day.
Friday -1 start day -5 end day.
Saturday -0 start day -6 end day.
It is 7 separate queries but does enable me to do what I was intending to do.