Datetime difference to return Days only? - python

$ cat .t.py
import re
from datetime import datetime as dtt
oldestDate = dateComp = dtt.strptime('1.1.1001', '%d.%m.%Y')
dateComp = dtt.strptime('11.1.2011', '%d.%m.%Y')
ind = re.sub(" days,.*", "", str((dateComp - oldestDate)))
print ind
print dateComp - oldestDate
$ python .t.py
368905
368905 days, 0:00:00
How can I get days only without the regex code-smell? The problem escalate because I need to use the index in many locations. So some cleaner way to do this?

Don't use str() so soon. The result you get back from subtracting one datetime from another is a timedelta object, which has a .days property that you can read.
(dateComp - oldestDate).days
Note that reading only the .days property will mean that it will round down the difference - if you instead want to round to the nearest number of days, you'll need to add some logic to check the .seconds property to see whether it's closer to 0 or 86400.

Related

How to Split a substract of a date in python

My code is the following:
date = datetime.datetime.now()- datetime.datetime.now()
print date
h, m , s = str(date).split(':')
When I print h the result is:
-1 day, 23
How do I get only the hour (the 23) from the substract using datetime?
Thanks.
If you subtract the current date from a past date, you would get a negative timedelta value.
You can get the seconds with td.seconds and corresponding hour value via just dividing by 3600.
from datetime import datetime
import time
date1 = datetime.now()
time.sleep(3)
date2 = datetime.now()
# timedelta object
td = date2 - date1
print(td.days, td.seconds // 3600, td.seconds)
# 0 0 3
You're not too far off but you should just ask your question as opposed to a question with a "real scenario" later as those are often two very different questions. That way you get an answer to your actual question.
All that said, rather than going through a lot of hoop-jumping with splitting the datetime object, assigning it to a variable which you then later use look for what you need in, it's better to just know what DateTime can do since that can be such a common part of your coding. You would also do well to look at timedelta (which is part of datetime) and if you use pandas, timestamp.
from datetime import datetime
date = datetime.now()
print(date)
print(date.hour)
I can get you the hour of datetime.datetime.now()
You could try indexing a list of a string of datetime.datetime.now():
print(list(str(datetime.datetime.now()))[11] + list(str(datetime.datetime.now()))[12])
Output (in my case when tested):
09
Hope I am of help!

Python : Is there a way to get the names of last three Month Names?

How can I extract last three month names in Python? If I am running this today then I would like to see May, June and July as my result.
Easier way is to use "%B" using datetime and timedelta
from dateutil.relativedelta import relativedelta
from datetime import datetime
today = datetime.now()
for i in range(1,4):
print((today - relativedelta(months=i)).strftime('%B'))
Output:
July
June
May
One way is to use the python calendar module, and list slice a month name for a given, extracted datetime month.
.month_name returns a list of all the month names.
calendar is part of the standard library.
For timedelta, there isn't a month parameter because the length of a month is not a constant value, so use days, as an approximation.
See datetime for the available methods.
datetime is part of the python standard library, so doesn't require a separate installation.
Use .month to extract the month from the datetime.
from datetime import datetime, timedelta
import calendar
# get the time now
now = datetime.now()
# iterate through 3 different timedeltas as an example
for x in range(1, 4):
new = now - timedelta(days=31*x)
print(calendar.month_name[new.month])
[out]:
July
June
May
As mentioned in the answer by bigbounty, using .strftime with '%B' is a better option than using calendar
However, unlike the dateutil module, timedelta still doesn't have a month parameter.
The dateutil module provides powerful extensions to the standard datetime module and must be installed, and then imported.
# get the time now
now = datetime.now()
# iterate through 3 different timedeltas as an example
for x in range(1, 4):
new = now - timedelta(days=31*x)
print(new.strftime('%B'))
[out]:
July
June
May
Best way to do this is a combination of the date and calendar modules.
date.today().month will give you a numerical value for the current month (1-12)
calendar.month_name[x] will give you the name for the month represented by the number x
the % operator will be used to wrap around the index of the month_name object to avoid the pesky 0 index returning ''
Putting them together we have:
from datetime import date
from calendar import month_name
def previous_n_months(n):
current_month_idx = date.today().month - 1 # Value is now (0-11)
for i in range(1, n+1):
# The mod operator will wrap the negative index back to the positive one
previous_month_idx = (current_month_idx - i) % 12 #(0-11 scale)
m = int(previous_month_idx + 1)
print(month_name[m])
Example usage:
>>> previous_n_months(3)
July
June
May

How to plus datetime in python?

I have the program that generate datetime in several format like below.
1 day, 21:21:00.561566
11:19:26.056148
Maybe it have in month or year format, and i want to know are there any way to plus these all time that i get from the program.
- 1 day, 21:21:00.561566 is the string representation of a datetime.timedelta object. If you need to parse from string to timedelta, pandas has a suitable method. There are other third party parsers; I'm just using this one since pandas is quite common.
import pandas as pd
td = pd.to_timedelta('- 11:19:26.056148')
# Timedelta('-1 days +12:40:33.943852')
td.total_seconds()
# -40766.056148
If you need to find the sum of multiple timedelta values, you can sum up their total_seconds and convert them back to timedelta:
td_strings = ['- 1 day, 21:21:00.561566', '- 11:19:26.056148']
td_sum = pd.Timedelta(seconds=sum([pd.to_timedelta(s).total_seconds() for s in td_strings]))
td_sum
# Timedelta('-1 days +10:01:34.505418')
...or leverage some tools from the Python standard lib:
from functools import reduce
from operator import add
td_sum = reduce(add, map(pd.to_timedelta, td_strings))
# Timedelta('-1 days +10:01:34.505418')
td_sum.total_seconds()
# -50305.494582
You can subtract date time like here to find how far apart these two times are:
https://stackoverflow.com/a/1345852/2415706
Adding two dates doesn't really make any sense though. Like, if you try to add Jan 1st of 2020 to Jan 1st of 1995, what are you expecting?
You can use datatime.timedelta class for this purpose.
You can find the documentation here.
You will need to parse your string and build a timedelta object.

how to create a date object in python representing a set number of days

I would like to define a variable to be a datetime object representing the number of days that is entered by the user. For example.
numDays = #input from user
deltaDatetime = #this is what I'm trying to figure out how to do
str(datetime.datetime.now() + deltaDatetime)
This code would print out a datetime representing 3 days from today if the user entered 3 as their input. Any idea how to do this? I'm completely lost as to an effective approach to this problem.
EDIT: Because of how my system is set up, the variable storing the "deltaDatetime" value must be a datetime value. As I said in the comments, something like 3 days becomes Year 0, January 3rd.
It's fairly straightforward using timedelta from the standard datetime library:
import datetime
numDays = 5 # heh, removed the 'var' in front of this (braincramp)
print datetime.datetime.now() + datetime.timedelta(days=numDays)
deltaDateTime = datetime.timedelta(days=3)
Use timedelta:
from datetime import datetime, timedelta
days = int(raw_input())
print datetime.now() + timedelta(days=days)

Attempting to insert an integer from a list into datetime object

What I am trying to accomplish is very simple: creating a loop from a range (pretty self explanatory below) that will insert the month into the datetime object. I know %d requires an integer, and I know that 'month' type is int...so I'm kind of stuck as to why I can't substitute my month variable. Here is my code:
all_months=range(1,13)
for month in all_months:
month_start = (datetime.date(2010,'%d',1))%month
next_month_begin= datetime.date(2010,'%d',1)%(month+1)
month_end=next_month_begin - timedelta(days=1)
print month_start
print month_end
What am I doing wrong?
All help appreciated! Thanks
There are a few things that you need to fix here.
EDIT: First, be careful with your range, since you are using month+1 to create next_month_begin, you do not want this to be greater than 12 or you will get an error.
Next, when you are trying to create the date object you are passing the month in as a string when you use (datetime.date(2010,'%d',1))%month. Your code probably throwing this error TypeError: an integer is required.
You need to give it the integer representing the month, not a string of the integer (there is a difference between 1 and '1'). This is also a simple fix, since you have variable named month that is already an integer, just use that instead of making a string. So you code should be something like:
month_start = datetime.date(2010,month,1)
I think you can figure out how to apply this to your next_month_begin assignment.
The last problem is that you need to use datetime.timedelta to tell Python to look in the datetime module for the timedelta() function -- your program would currently give you an error saying that timedelta is not defined.
Let me know if you have any problems applying these fixes. Be sure to include what the error you may be getting as well.
You've got other answers, but here's a way to get the last day of the month. Adding 31 days will get you into the next month regardless of the number of days in the current month, then moving back to the first and subtracting a day will give the ending date.
import datetime
for month in range(1,13):
month_start = datetime.date(2010,month,1)
into_next_month = month_start + datetime.timedelta(days=31)
month_end = into_next_month.replace(day=1) - datetime.timedelta(days=1)
print month_start,month_end
month is a variable and you can use it to create the datetime object. I think you want to do the following:
month_start = datetime.date(2010, month, 1)
next_month_begin = datetime.date(2010, month+1, 1)
That will work, because datetime.date() requires 3 integer arguments. '%d' % month would instead format the integer month as string. '%04d' % 3 for example would format the number 3 with 4 digits and leading zeros. But it's important to know, that even the (nearly unformatted) string "3" is different to the number 3 in Python.
And you can't write datetime(...) % 3 because the % operator will only work when used on a format string like the previous "%03d" % 3 example and not on a datetime object.
But other types might also accept the % operator (not including datetime objects). For example, integers accept the % operator to get the remainder of a division: 3 % 2 # returns 1. But there, the meaning of % is completely different, because the meaning of the operator depends on the types involved. For example, try 3 + 2 and "3" + "2". There, the meaning of + differs (integer addition vs. string concatenation), because the types are different too.
Check out the calendar module (http://docs.python.org/library/calendar.html).
It has batteries included for this sort of thing...
You could just do:
from calendar import Calendar
def start_and_end_days(year, month):
cal = Calendar()
month_days = [day for day in cal.itermonthdays(year, month) if day.month == month]
first_day = month_days[0]
last_day = month_days[-1]
return (first_day, last_day)

Categories

Resources