From 086e1b187dc89bfbd781ba5df476baaae6701ced Mon Sep 17 00:00:00 2001 From: Brock Date: Thu, 17 Sep 2020 19:24:23 -0700 Subject: [PATCH] REF: share insert between DTI/TDI/PI --- pandas/core/indexes/datetimelike.py | 82 ++++++++++++++++------------- pandas/core/indexes/period.py | 6 +-- 2 files changed, 47 insertions(+), 41 deletions(-) diff --git a/pandas/core/indexes/datetimelike.py b/pandas/core/indexes/datetimelike.py index 122977eee99fb..1ab40a76b30ff 100644 --- a/pandas/core/indexes/datetimelike.py +++ b/pandas/core/indexes/datetimelike.py @@ -575,6 +575,50 @@ def delete(self, loc): arr = type(self._data)._simple_new(new_i8s, dtype=self.dtype, freq=freq) return type(self)._simple_new(arr, name=self.name) + def insert(self, loc: int, item): + """ + Make new Index inserting new item at location + + Parameters + ---------- + loc : int + item : object + if not either a Python datetime or a numpy integer-like, returned + Index dtype will be object rather than datetime. + + Returns + ------- + new_index : Index + """ + item = self._data._validate_insert_value(item) + + freq = None + if is_period_dtype(self.dtype): + freq = self.freq + elif self.freq is not None: + # freq can be preserved on edge cases + if self.size: + if item is NaT: + pass + elif (loc == 0 or loc == -len(self)) and item + self.freq == self[0]: + freq = self.freq + elif (loc == len(self)) and item - self.freq == self[-1]: + freq = self.freq + else: + # Adding a single item to an empty index may preserve freq + if self.freq.is_on_offset(item): + freq = self.freq + + arr = self._data + item = arr._unbox_scalar(item) + item = arr._rebox_native(item) + + new_values = np.concatenate([arr._ndarray[:loc], [item], arr._ndarray[loc:]]) + new_arr = self._data._from_backing_data(new_values) + new_arr._freq = freq + + return type(self)._simple_new(new_arr, name=self.name) + # -------------------------------------------------------------------- # Join/Set Methods @@ -895,45 +939,11 @@ def _maybe_utc_convert(self, other): # -------------------------------------------------------------------- # List-Like Methods + @Appender(DatetimeIndexOpsMixin.insert.__doc__) def insert(self, loc, item): - """ - Make new Index inserting new item at location - - Parameters - ---------- - loc : int - item : object - if not either a Python datetime or a numpy integer-like, returned - Index dtype will be object rather than datetime. - - Returns - ------- - new_index : Index - """ if isinstance(item, str): # TODO: Why are strings special? # TODO: Should we attempt _scalar_from_string? return self.astype(object).insert(loc, item) - item = self._data._validate_insert_value(item) - - freq = None - # check freq can be preserved on edge cases - if self.freq is not None: - if self.size: - if item is NaT: - pass - elif (loc == 0 or loc == -len(self)) and item + self.freq == self[0]: - freq = self.freq - elif (loc == len(self)) and item - self.freq == self[-1]: - freq = self.freq - else: - # Adding a single item to an empty index may preserve freq - if self.freq.is_on_offset(item): - freq = self.freq - - item = self._data._unbox_scalar(item) - - new_i8s = np.concatenate([self[:loc].asi8, [item], self[loc:].asi8]) - arr = type(self._data)._simple_new(new_i8s, dtype=self.dtype, freq=freq) - return type(self)._simple_new(arr, name=self.name) + return DatetimeIndexOpsMixin.insert(self, loc, item) diff --git a/pandas/core/indexes/period.py b/pandas/core/indexes/period.py index 42dce1bd53f22..900d3f9f1866b 100644 --- a/pandas/core/indexes/period.py +++ b/pandas/core/indexes/period.py @@ -436,11 +436,7 @@ def insert(self, loc, item): if not isinstance(item, Period) or self.freq != item.freq: return self.astype(object).insert(loc, item) - i8result = np.concatenate( - (self[:loc].asi8, np.array([item.ordinal]), self[loc:].asi8) - ) - arr = type(self._data)._simple_new(i8result, dtype=self.dtype) - return type(self)._simple_new(arr, name=self.name) + return DatetimeIndexOpsMixin.insert(self, loc, item) def join(self, other, how="left", level=None, return_indexers=False, sort=False): """