Skip to content

Commit 1fb8811

Browse files
Backport PR #48555 on branch 1.5.x (DEPR: Series.astype(np.datetime64)) (#48569)
Backport PR #48555: DEPR: Series.astype(np.datetime64) Co-authored-by: jbrockmendel <[email protected]>
1 parent 19a3f5a commit 1fb8811

File tree

4 files changed

+36
-0
lines changed

4 files changed

+36
-0
lines changed

doc/source/whatsnew/v1.5.0.rst

+1
Original file line numberDiff line numberDiff line change
@@ -936,6 +936,7 @@ Other Deprecations
936936
- Deprecated the ``sort_columns`` argument in :meth:`DataFrame.plot` and :meth:`Series.plot` (:issue:`47563`).
937937
- Deprecated positional arguments for all but the first argument of :meth:`DataFrame.to_stata` and :func:`read_stata`, use keyword arguments instead (:issue:`48128`).
938938
- Deprecated the ``mangle_dupe_cols`` argument in :func:`read_csv`, :func:`read_fwf`, :func:`read_table` and :func:`read_excel`. The argument was never implemented, and a new argument where the renaming pattern can be specified will be added instead (:issue:`47718`)
939+
- Deprecated allowing ``dtype='datetime64'`` or ``dtype=np.datetime64`` in :meth:`Series.astype`, use "datetime64[ns]" instead (:issue:`47844`)
939940

940941
.. ---------------------------------------------------------------------------
941942
.. _whatsnew_150.performance:

pandas/core/arrays/datetimes.py

+16
Original file line numberDiff line numberDiff line change
@@ -630,6 +630,22 @@ def astype(self, dtype, copy: bool = True):
630630
return type(self)._simple_new(res_values, dtype=dtype)
631631
# TODO: preserve freq?
632632

633+
elif (
634+
self.tz is None
635+
and is_datetime64_dtype(dtype)
636+
and dtype != self.dtype
637+
and is_unitless(dtype)
638+
):
639+
# TODO(2.0): just fall through to dtl.DatetimeLikeArrayMixin.astype
640+
warnings.warn(
641+
"Passing unit-less datetime64 dtype to .astype is deprecated "
642+
"and will raise in a future version. Pass 'datetime64[ns]' instead",
643+
FutureWarning,
644+
stacklevel=find_stack_level(inspect.currentframe()),
645+
)
646+
# unit conversion e.g. datetime64[s]
647+
return self._ndarray.astype(dtype)
648+
633649
elif is_period_dtype(dtype):
634650
return self.to_period(freq=dtype.freq)
635651
return dtl.DatetimeLikeArrayMixin.astype(self, dtype, copy)

pandas/core/indexes/base.py

+6
Original file line numberDiff line numberDiff line change
@@ -42,6 +42,7 @@
4242
IncompatibleFrequency,
4343
OutOfBoundsDatetime,
4444
Timestamp,
45+
is_unitless,
4546
tz_compare,
4647
)
4748
from pandas._typing import (
@@ -1085,6 +1086,11 @@ def astype(self, dtype, copy: bool = True):
10851086

10861087
values = self._data
10871088
if isinstance(values, ExtensionArray):
1089+
if isinstance(dtype, np.dtype) and dtype.kind == "M" and is_unitless(dtype):
1090+
# TODO(2.0): remove this special-casing once this is enforced
1091+
# in DTA.astype
1092+
raise TypeError(f"Cannot cast {type(self).__name__} to dtype")
1093+
10881094
with rewrite_exception(type(values).__name__, type(self).__name__):
10891095
new_values = values.astype(dtype, copy=copy)
10901096

pandas/tests/series/methods/test_astype.py

+13
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,19 @@
3030

3131

3232
class TestAstypeAPI:
33+
def test_astype_unitless_dt64_deprecated(self):
34+
# GH#47844
35+
ser = Series(["1970-01-01", "1970-01-01", "1970-01-01"], dtype="datetime64[ns]")
36+
37+
msg = "Passing unit-less datetime64 dtype to .astype is deprecated and "
38+
with tm.assert_produces_warning(FutureWarning, match=msg):
39+
res = ser.astype(np.datetime64)
40+
tm.assert_series_equal(ser, res)
41+
42+
with tm.assert_produces_warning(FutureWarning, match=msg):
43+
res = ser.astype("datetime64")
44+
tm.assert_series_equal(ser, res)
45+
3346
def test_arg_for_errors_in_astype(self):
3447
# see GH#14878
3548
ser = Series([1, 2, 3])

0 commit comments

Comments
 (0)