40

I have a datetime64 t that I'd like to represent as a string.

When I call strftime like this t.strftime('%Y.%m.%d') I get this error:

AttributeError: 'numpy.datetime64' object has no attribute 'strftime'

What am I missing? I am using Python 3.4.2 and Numpy 1.9.1

deeb
  • 1,332
  • 4
  • 15
  • 27
  • Are you wanting to use `datetime.datetime.strftime` instead? so `import datetime as dt dt.datetime.strftime(t, '%Y.%m.%d')` I think should work – EdChum Feb 04 '15 at 17:01
  • 1
    I saw examples that looked like datetime64 had a strftime method itself. I tried your solution and got this: `TypeError: descriptor 'strftime' requires a 'datetime.date' object but received a 'numpy.datetime64'` – deeb Feb 04 '15 at 17:04
  • duplicate http://stackoverflow.com/questions/19502506/convert-numpy-datetime64-to-string-object-in-python ? (though `str(dt)` may be all you need?) – Andy Hayden Feb 04 '15 at 17:18
  • Andy, that is the solution I am trying to implement but I can't call the `ts.strftime` part for some reason. – deeb Feb 04 '15 at 17:25

6 Answers6

53

Importing a data structures library like pandas to accomplish type conversion feels like overkill to me. You can achieve the same thing with the standard datetime module:

import numpy as np
import datetime
t = np.datetime64('2017-10-26')
t = t.astype(datetime.datetime)
timestring = t.strftime('%Y.%m.%d')
apteryx
  • 1,105
  • 7
  • 14
  • 18
    This should be the accepted answer. It would be ridiculous to have Pandas as a project dependency just to convert a date. – titusjan May 21 '18 at 12:22
  • 2
    It would be even more ridiculous to have Pandas as a project dependency to _print_ a date. – Joooeey Nov 21 '18 at 22:08
  • 3
    It should also be noted that this is actually also a significantly faster method. Using timeit I found `t.astype(datetime.datetime).strftime('%Y.%m.%d')` took 5.86 µs ± 339 ns per loop while `pd.to_datetime(t).strftime('%Y.%m.%d')` took 35.8 µs ± 252 ns per loop. – n8yoder Apr 18 '19 at 17:47
  • 1
    `astype()` was giving me a hassle dealing with a `datetime` I added to a Pandas DF (lots of type conversion here), and `pd.to_datetime()` worked perfectly. – xtian Sep 20 '20 at 20:11
  • 2
    I'd agree with @titusjan, but somehow i was getting int by t.astype(datetime.datetime) in my particular case, where np.datetime64 is comming from part of xarray . In my particular case user-12321 method made more sense. pandas seems to have more thorough handling of datetime related objects – yosukesabai Jan 05 '21 at 20:59
  • This doesn't answer the question directly. You're referring to another answer to say what not to do, but you haven't explained to the question asker why you can't use .strftime on their object – Thering Nov 23 '22 at 17:25
38

Use this code:

import pandas as pd 
t= pd.to_datetime(str(date)) 
timestring = t.strftime('%Y.%m.%d')
user 12321
  • 2,846
  • 1
  • 24
  • 34
  • 3
    I am doing this but strftime is not defined – deeb Feb 04 '15 at 23:45
  • 3
    @deeb before using `strftime` convert your object to pandas datetime using `pd.to_datetime(x)` otherwise it will be considered as an numpy.datetime64 – Ikbel Apr 26 '19 at 12:48
22

This is the simplest way:

t.item().strftime('%Y.%m.%d')

item() gives you a Python native datetime object, on which all the usual methods are available.

John Zwinck
  • 239,568
  • 38
  • 324
  • 436
  • I think this is an even better solution than explicitly using the built-in `datetime` module. – Fanchen Bao Jan 23 '21 at 00:04
  • 5
    I get this error on my `numpy.datetime64('2021-11-01T00:00:00.000000000')` : `AttributeError: 'int' object has no attribute 'strftime' ` – SCool Nov 09 '21 at 16:02
  • 1
    @SCool: Your issue is explained in David Wasserman's answer here, which is that nanosecond-precision timestamps are not supported by the Python standard library, so `item()` on your type (which is sometimes known as `m8[ns]` gives an integer rather than a datetime. If you use 6 or fewer digits after the decimal, it will work. – John Zwinck Nov 11 '21 at 12:50
8

If your goal is only to represent t as a string, the simplest solution is str(t). If you want it in a specific format, you should use one of the solutions above.

One caveat is that np.datetime64 can have different amounts of precision. If t has nanosecond precision, user 12321's solution will still work, but apteryx's and John Zwinck's solutions won't, because t.astype(datetime.datetime) and t.item() return an int:

import numpy as np

print('second precision')
t = np.datetime64('2000-01-01 00:00:00') 
print(t)
print(t.astype(datetime.datetime))
print(t.item())

print('microsecond precision')
t = np.datetime64('2000-01-01 00:00:00.0000') 
print(t)
print(t.astype(datetime.datetime))
print(t.item())

print('nanosecond precision')
t = np.datetime64('2000-01-01 00:00:00.0000000') 
print(t)
print(t.astype(datetime.datetime))
print(t.item())
import pandas as pd 
print(pd.to_datetime(str(t)))


second precision
2000-01-01T00:00:00
2000-01-01 00:00:00
2000-01-01 00:00:00
microsecond precision
2000-01-01T00:00:00.000000
2000-01-01 00:00:00
2000-01-01 00:00:00
nanosecond precision
2000-01-01T00:00:00.000000000
946684800000000000
946684800000000000
2000-01-01 00:00:00
David Wasserman
  • 551
  • 5
  • 10
  • 4
    I have made this [an issue](https://github.com/numpy/numpy/issues/18363) since it should be a bug. Also, another way to get the correct datetime is the (ugly) workaround: `t.astype('datetime64[us]').astype(datetime.datetime)` if you do not want to use pandas – Fee Feb 08 '21 at 12:39
  • Thanks a lot for this workaround @GevaertJoep !! (it's rare to find something that useful in a comment of the last answer) I was about to give up and use the slower panda method – jmd Jul 27 '21 at 16:16
  • Wow! Just coming to Python from a C# and C++ background. Cannot believe that something as simple as formatting a date for output requires pages and pages of explanation. I have now wasted 30 minutes on something that should have taken 30 seconds. What a horrible abomination of a programming language! – Phil Degenhardt Jun 15 '22 at 22:45
  • @PhilDegenhardt I was happy when I could move out from JavaScript's horrible date system. C# is perfect. Now they again force using Python in a lot of places. Congrats... – klenium Jul 06 '22 at 15:37
5

For those who might stumble upon this: numpy now has a numpy.datetime_as_string function. Only caveat is that it accepts an array rather than just an individual value. I could make however that this is still a better solution than having to use another library just to do the conversion.

adrianp
  • 999
  • 1
  • 8
  • 13
  • 2
    But `numpy.datetime_as_string` does not seem to support formatting of the output string, which makes it less useful than the other methods leveraging the built-in `datetime` object. – Fanchen Bao Jan 23 '21 at 00:07
-2

It might help to convert the datetime object to string and use splitting as shown below:

dtObj = 2011-08-01T00:00:00.000000000

dtString = str(dtObj).split('-01T00:00:00.000000000')[0]

print(dtString)

>>> '2011-08-01'

moinabyssinia
  • 163
  • 1
  • 2
  • 9