I'm pretty new to Python and App Engine, but what I'm trying to do is store a model which contains a DateProperty, and that DateProperty is populated with a Date entered by the user in a web form.
I've got the model of:
class Memory(db.Model):
author = db.UserProperty()
content = db.StringProperty(multiline=True)
date = db.DateProperty()
and then create an instance with:
memory = Memory()
memory.author = users.get_current_user()
memory.content = self.request.get('content')
But as soon as I try to do anything with the date value, I break it. I'm assuming - and entering - the date value in this format: 2009-07-21
I've tried:
memory.date = time.strptime(self.request.get('date'), '%Y-%m-%d')
memory.date = db.DateProperty(self.request.get('date'))
memory.date = self.request.get('date') (wishful thinking I guess)
and a few other options I can't even remember now. Everything I try leads to an ImportError with a giant stack trace ending in:
: No
module named _multiprocessing
args = ('No module named _multiprocessing',)
message = 'No module named _multiprocessing'
I have no idea what to make of that.
I come from a PHP world where strtotime() was my magic function that gave me everything I needed for conversions, and the date() function could handle the rest of the formatting. Now I see things with inline lambda (??) functions and what not.
What am I missing on something that would seem to be so simple.
perhaps you are using the wrong class? I'm not sure what type your model should take
but try:
from datetime import datetime
myValue = datetime.strptime(self.request.get('date'), '%Y-%m-%d')
I use a datetime object in MySQL with MySQLdb (and a datetime field)
...likewise you can try
from datetime import datetime
myValue = datetime.strptime(self.request.get('date'), '%Y-%m-%d').date()
(notice the [obj].date() at the end)
Yeah, PHP's is much nicer. I'm using this library
http://labix.org/python-dateutil
>>> import dateutil.parser
>>> dateutil.parser.parse("may 2 1984")
datetime.datetime(1984, 5, 2, 0, 0)
You were right with strptime:
>>> dt = time.strptime('2009-07-21', '%Y-%m-%d')
>>> dt
time.struct_time(tm_year=2009, tm_mon=7, tm_mday=21, tm_hour=0, tm_min=0, tm_sec
=0, tm_wday=1, tm_yday=202, tm_isdst=-1)
>>>
You got struct that can be used by other functions. For example display date in M/D/Y convention:
>>> time.strftime('%m/%d/%Y', dt)
'07/21/2009'
Another example (import datetime module):
>>> dt = datetime.datetime.strptime('2009-07-21', '%Y-%m-%d')
>>> td = datetime.timedelta(days=20)
>>> dt+td
datetime.datetime(2009, 8, 10, 0, 0)
Related
Is there any way to automatically parse strings with time only to datetime.time object (or something similar)? Same for datetime.date.
I've tried dateutil, arrow, moment, pandas.to_datetime.
All these parsers create timestamps with a current date.
>>> from dateutil.parser import parse
>>> parse('23:53')
datetime.datetime(2019, 1, 8, 23, 53) # datetime.time(23, 53) expected
>>> parse('2018-01-04')
datetime.datetime(2018, 1, 4, 0, 0) # datetime.date(2018, 1, 4) expected
UPD:
Thanks for the responses. Think that I should clarify the problem.
The program doesn't know what will be in the input (timestamp, date or time), and it should decide to set appropriate type. The problem is to distinguish these types.
For example, I can parse 23:53 and get a timestamp. How can I decide to extract the time from it or not?
You can use fromisoformat() from datetime.
import datetime
datetime.time.fromisoformat('23:53')
datetime.date.fromisoformat('2018-01-04')
What you basically want is for '23:53' to become a datetime.time object and for '2018-01-04' to become a datetime.date object. This cannot be achieved by using dateutil.parser.parse():
Returns a datetime.datetime object or, if the fuzzy_with_tokens option is True, returns a tuple, the first element being a datetime.datetime object, the second a tuple containing the fuzzy tokens.
From the documentation. So you'll always get a datetime.datetime object when using dateutil.parser.parse()
I would guess you need to interpret the input string yourself to define wether you're trying to parse a time or a date. When you do that, you can still use the dateutil.parser.parse() function to get the object you want:
from dateutil.parser import parse
my_time = parse('23:53')
my_time.time() # datetime.time(23, 53)
my_time.date() # datetime.date(2019, 1, 8)
Here you have an example. Just set the date attributes with replace, and select the output with strftime.
import datetime
date = datetime.datetime.now()
newdate = date.replace(hour=11, minute=59)
print(newdate.strftime('%H:%M'))
newdate2 = date.replace(year=2014, month=1, day=3)
print(newdate2.strftime('%Y-%m-%d'))
You can use either time or datetime modules, but one thing to bear in mind, is that these always create an object, that specifies a moment in time. (Also, if parsing strings, consider using the strptime function and displaying as string, strftime function respectively)
e.g.
>>> hours = time.strptime("23:59", "%H:%M")
>>> days = time.strptime("2018-01-04", "%Y-%m-%d")
>>> time.strftime("%H:%M", hours)
'23:59'
>>> time.strftime("%H:%M %Y", hours)
'23:59 1900'
Not recommended, but if you wish to separate these two object for some reason and wish to only care for a specific portion of your assignement, you can still adress the respective numbers with
>>> hours.tm_hour
23
>>> hours.tm_min
59
>>> days.tm_mon
1
>>> days.tm_mday
4
>>> days.tm_year
2018
A far better approach, in my opinion would be formatting the complete date string and using the strptime to form a complete timestamp - even if you get the time and date as separate inputs:
>>> ttime = "22:45"
>>> dday = "2018-01-04"
You can use the % formatter, or the "new" python f-Strings
>>> complete_t_string = "{} {}".format(dday, ttime)
>>> complete_t_string
'2018-01-04 22:45'
Now that we have a complete string, we can specify how it should be read and create a complete timestamp:
>>> complete_time = time.strptime(complete_t_string, "%Y-%m-%d %H:%M")
>>> complete_time
time.struct_time(tm_year=2018, tm_mon=1, tm_mday=4, tm_hour=22, tm_min=45, tm_sec=0, tm_wday=3, tm_yday=4, tm_isdst=-1)
EDIT:
Somebody will probably kill me, but if you absolutely know that you will only get two types of values, you could just do a simple try / except construct. It can probably be written more Pythonically:
try:
time.strptime(t_string, "%H:%M")
except ValueError:
time.strptime(t_string, "%Y-%m-%d")
I have a string output from another program that shows the date as
16/05/03 # (YY/MM/DD)
and I wish to change it to
03/05/16 #(DD/MM/YY)
and here is how the date is supplied
(date = info[4].replace('"', '')
i have tried
dates = str(date)[::-1]
but that gave me an output of
40/50/61
not quite what I wanted
any ideas using a minimal code as possible?
>>> '/'.join('16/05/03'.split('/')[::-1])
'03/05/16'
or
>>> '/'.join(reversed('16/05/03'.split('/')))
'03/05/16'
or using datetime library:
>> from datetime import datetime
>>> datetime.strftime(datetime.strptime('16/05/03', '%y/%m/%d'), '%d/%m/%y')
'03/05/16'
Using datetime give you alot more control with changing the format to suite what you want.
import datetime
d = datetime.strptime('16/05/03', '%y/%m/%d')
print d.strftime('%d/%m/%y')
I have a datetime object and I'm trying to individually get a string with the date, and one with the time. I'd like the values for theDate and theTime to be strings.
theDate = myDatetime.date()
theTime = myDatetime.time()
Something along those lines. I tried str(datetime.date) but it gave me a reference in memory, any other ideas? Thanks in advance for any help.
Use the datetime.strftime() method on the datetime object:
theDate = myDatetime.strftime('%Y-%m-%d')
theTime = myDatetime.strftime('%H:%M:%S')
Alternatively, turn your date and time objects into strings for their default string representations:
theDate = str(myDatetime.date())
theTime = str(myDatetime.time())
Demo:
>>> import datetime
>>> myDatetime = datetime.datetime.now()
>>> myDatetime.strftime('%Y-%m-%d')
'2013-06-19'
>>> myDatetime.strftime('%H:%M:%S')
'16:49:44'
>>> str(myDatetime.date())
'2013-06-19'
>>> str(myDatetime.time())
'16:49:44.447010'
The default string format for datetime.time objects includes the microsecond component.
I've RTFM and read many questions and answers here on SO regarding this, and was happily using strftime and strptime yesterday, so I would swear this should work, but it isn't....
I just want an integer. Not a "timedelta object." Not an "aware yet hashable object" (see, I RTFM). Not a tuple. Not a dictionary. Just a simple freaking integer so I can use an if statement and branch and be happy. Please bring the light of your wisdom upon this, with thanks.
Here's what I have
...
import datetime
mdate = "2010-10-05"
rdate = "2010-10-05"
mdate1 = datetime.strptime(mdate, "%Y-%m-%d")
rdate1 = datetime.strptime(rdate, "%Y-%m-%d")
delta = datetime.timedelta.days(mdate1 - rdate1)
Here's what I get:
pmain.py:4: AttributeError: 'module' object has no attribute 'strptime'
(error hits in the 'mdate1..." line above)
And, that doesn't mean that my delta line is going to work -- please look at that one, too.
You want to get the classmethod datetime.datetime.strptime(), then take the .days attribute from the resulting timedelta:
import datetime
mdate = "2010-10-05"
rdate = "2010-10-05"
mdate1 = datetime.datetime.strptime(mdate, "%Y-%m-%d").date()
rdate1 = datetime.datetime.strptime(rdate, "%Y-%m-%d").date()
delta = (mdate1 - rdate1).days
So you have the datetime module, which has a datetime.datetime class, which in turn has a datetime.datetime.strptime() method on it. I also added calls to .date() to extract just the date portion (result is a datetime.date instance); this makes dealing with timestamps that differ slightly less than a multiple of 24 hours easier.
Demo:
>>> import datetime
>>> mdate = "2010-10-05"
>>> rdate = "2010-10-05"
>>> mdate1 = datetime.datetime.strptime(mdate, "%Y-%m-%d").date()
>>> rdate1 = datetime.datetime.strptime(rdate, "%Y-%m-%d").date()
>>> delta = (mdate1 - rdate1).days
>>> print delta
0
>>> type(delta)
<type 'int'>
sign1['days'] = sign1['diff'] / np.timedelta64(1, 'D')
I had the same problem and it solved by uding the above statement.
I hope it helps.
import datetime
mdate = "2010-11-05"
rdate = "2010-10-05"
mdate1 = datetime.datetime.strptime(mdate, "%Y-%m-%d")
rdate1 = datetime.datetime.strptime(rdate, "%Y-%m-%d")
delta = (mdate1 - rdate1).days
I'm adding UTC time strings to Bitbucket API responses that currently only contain Amsterdam (!) time strings. For consistency with the UTC time strings returned elsewhere, the desired format is 2011-11-03 11:07:04 (followed by +00:00, but that's not germane).
What's the best way to create such a string (without a microsecond component) from a datetime instance with a microsecond component?
>>> import datetime
>>> print unicode(datetime.datetime.now())
2011-11-03 11:13:39.278026
I'll add the best option that's occurred to me as a possible answer, but there may well be a more elegant solution.
Edit: I should mention that I'm not actually printing the current time – I used datetime.now to provide a quick example. So the solution should not assume that any datetime instances it receives will include microsecond components.
If you want to format a datetime object in a specific format that is different from the standard format, it's best to explicitly specify that format:
>>> import datetime
>>> datetime.datetime.now().strftime("%Y-%m-%d %H:%M:%S")
'2011-11-03 18:21:26'
See the documentation of datetime.strftime() for an explanation of the % directives.
Starting from Python 3.6, the isoformat() method is flexible enough to also produce this format:
datetime.datetime.now().isoformat(sep=" ", timespec="seconds")
>>> import datetime
>>> now = datetime.datetime.now()
>>> print unicode(now.replace(microsecond=0))
2011-11-03 11:19:07
In Python 3.6:
from datetime import datetime
datetime.now().isoformat(' ', 'seconds')
'2017-01-11 14:41:33'
https://docs.python.org/3.6/library/datetime.html#datetime.datetime.isoformat
This is the way I do it. ISO format:
import datetime
datetime.datetime.now().replace(microsecond=0).isoformat()
# Returns: '2017-01-23T14:58:07'
You can replace the 'T' if you don't want ISO format:
datetime.datetime.now().replace(microsecond=0).isoformat(' ')
# Returns: '2017-01-23 15:05:27'
Yet another option:
>>> import time
>>> time.strftime("%Y-%m-%d %H:%M:%S")
'2011-11-03 11:31:28'
By default this uses local time, if you need UTC you can use the following:
>>> time.strftime("%Y-%m-%d %H:%M:%S", time.gmtime())
'2011-11-03 18:32:20'
Keep the first 19 characters that you wanted via slicing:
>>> str(datetime.datetime.now())[:19]
'2011-11-03 14:37:50'
I usually do:
import datetime
now = datetime.datetime.now()
now = now.replace(microsecond=0) # To print now without microsecond.
# To print now:
print(now)
output:
2019-01-13 14:40:28
Since not all datetime.datetime instances have a microsecond component (i.e. when it is zero), you can partition the string on a "." and take only the first item, which will always work:
unicode(datetime.datetime.now()).partition('.')[0]
As of Python 3.6+, the best way of doing this is by the new timespec argument for isoformat.
isoformat(timespec='seconds', sep=' ')
Usage:
>>> datetime.now().isoformat(timespec='seconds')
'2020-10-16T18:38:21'
>>> datetime.now().isoformat(timespec='seconds', sep=' ')
'2020-10-16 18:38:35'
We can try something like below
import datetime
date_generated = datetime.datetime.now()
date_generated.replace(microsecond=0).isoformat(' ').partition('+')[0]
>>> from datetime import datetime
>>> dt = datetime.now().strftime("%Y-%m-%d %X")
>>> print(dt)
'2021-02-05 04:10:24'
f-string formatting
>>> import datetime
>>> print(f'{datetime.datetime.now():%Y-%m-%d %H:%M:%S}')
2021-12-01 22:10:07
This I use because I can understand and hence remember it better (and date time format also can be customized based on your choice) :-
import datetime
moment = datetime.datetime.now()
print("{}/{}/{} {}:{}:{}".format(moment.day, moment.month, moment.year,
moment.hour, moment.minute, moment.second))
I found this to be the simplest way.
>>> t = datetime.datetime.now()
>>> t
datetime.datetime(2018, 11, 30, 17, 21, 26, 606191)
>>> t = str(t).split('.')
>>> t
['2018-11-30 17:21:26', '606191']
>>> t = t[0]
>>> t
'2018-11-30 17:21:26'
>>>
You can also use the following method
import datetime as _dt
ts = _dt.datetime.now().timestamp()
print("TimeStamp without microseconds: ", int(ts)) #TimeStamp without microseconds: 1629275829
dt = _dt.datetime.now()
print("Date & Time without microseconds: ", str(dt)[0:-7]) #Date & Time without microseconds: 2021-08-18 13:07:09
Current TimeStamp without microsecond component:
timestamp = list(str(datetime.timestamp(datetime.now())).split('.'))[0]