pandas-dev/pandas · error · TypeError

Cannot add or subtract timedelta64[ns] dtype from

Error message

Cannot add or subtract timedelta64[ns] dtype from {self.dtype}

What it means

Raised by PeriodArray._time_shift (the timedelta add/subtract path) when self.dtype._is_tick_like() is False. Only tick-like periods (second, minute, hour, day and their multiples) have a direct, unambiguous timedelta64 unit; higher-level periods (week, month, quarter, year) have variable lengths, so adding a raw timedelta64[ns] is undefined and rejected. The dtype is shown in the message.

Solutions

  1. Use integer offsets with the period's own freq: idx + 1 * idx.freq (shifts by one period).
  2. Convert to tick-like via .asfreq('D'/'h'/...) before timedelta arithmetic, then convert back if needed.
  3. Use Timestamp arithmetic (.to_timestamp()) if you truly need nanosecond-resolution deltas.

Example fix

# before
idx = pd.period_range('2023', periods=3, freq='Y')
idx + pd.Timedelta('1D')  # raises

# after
idx + 1 * idx.freq          # shift by one year
# or
idx.asfreq('D') + pd.Timedelta('1D')
Defensive patterns

Strategy: type-guard

Validate before calling

import pandas as pd

def shift_period(period_idx, delta):
    if isinstance(delta, (pd.Timedelta,)) and not period_idx.dtype._is_tick_like():
        # convert delta to a number of periods
        return period_idx + (delta // period_idx.freq.base)
    return period_idx + delta

Type guard

def is_tick_like_period(period_idx) -> bool:
    return period_idx.dtype._is_tick_like()

Try / catch

try:
    period_idx + delta
except TypeError as e:
    if 'Cannot add or subtract timedelta' in str(e):
        period_idx.asfreq('D') + delta  # downgrade to tick-like
    else:
        raise

Prevention

When it happens

Trigger: yearly_idx + pd.Timedelta('1D'); monthly_idx - np.timedelta64(1, 'h'); pd.period_range('2023', freq='Y')[0] + pd.Timedelta(hours=1). Any +/- with a Timedelta/TimedeltaArray on a non-tick PeriodArray.

Common situations: Treating all period types as if they were fixed-length; porting datetime arithmetic to period arithmetic without accounting for variable-length periods; business-calendar code.

Related errors


AI-assisted analysis of pandas-dev/pandas@3b7651241d (2026-08-11). Data as JSON: /api/errors/ebf3801ff4760837. Report an issue: GitHub.

Appendix: source

Thrown at pandas/core/arrays/period.py:1268

        else:
            td = np.asarray(Timedelta(other).asm8)
        return self._add_timedelta_arraylike(td)

    def _add_timedelta_arraylike(
        self, other: TimedeltaArray | npt.NDArray[np.timedelta64]
    ) -> Self:
        """
        Parameters
        ----------
        other : TimedeltaArray or ndarray[timedelta64]

        Returns
        -------
        PeriodArray
        """
        if not self.dtype._is_tick_like():
            # We cannot add timedelta-like to non-tick PeriodArray
            raise TypeError(
                f"Cannot add or subtract timedelta64[ns] dtype from {self.dtype}"
            )

        dtype = np.dtype(f"m8[{self.dtype._td64_unit}]")

        # Similar to _check_timedeltalike_freq_compat, but we raise with a
        #  more specific exception message if necessary.
        try:
            delta = astype_overflowsafe(
                np.asarray(other), dtype=dtype, copy=False, round_ok=False
            )
        except ValueError as err:
            # e.g. if we have minutes freq and try to add 30s
            # "Cannot losslessly convert units"
            raise IncompatibleFrequency(
                "Cannot add/subtract timedelta-like from PeriodArray that is "
                "not an integer multiple of the PeriodArray's freq."
            ) from err

View on GitHub (pinned to 3b7651241d)