pandas-dev/pandas · error · TypeError

cumprod not supported for Timedelta.

Error message

cumprod not supported for Timedelta.

What it means

TimedeltaArray._accumulate raises TypeError for cumprod because cumulative product of time deltas is undefined (multiplying durations is not meaningful). cumsum is supported; cummin and cummax are inherited; cumprod is explicitly refused.

Solutions

  1. Drop cumprod from operations applied to timedelta columns.
  2. If the values represent integers-as-durations, extract the numeric component first (.dt.total_seconds()) then cumprod.
  3. Use cumsum if the goal was cumulative addition of durations.

Example fix

// before
s = pd.Series(pd.to_timedelta(['1 day','2 days']))
s.cumprod()  # TypeError
// after
s.dt.total_seconds().cumprod()
Defensive patterns

Strategy: type-guard

Validate before calling

def safe_cumprod(s):
    if pd.api.types.is_timedelta64_dtype(s):
        raise TypeError('cumprod not supported for timedelta')
    return s.cumprod()

Type guard

def cumprod_safe_dtype(series) -> bool:
    return pd.api.types.is_numeric_dtype(series)

Try / catch

try:
    s.cumprod()
except TypeError as e:
    if 'cumprod not supported for Timedelta' in str(e):
        s.dt.total_seconds().cumprod()
    else:
        raise

Prevention

When it happens

Trigger: s.cumprod() on a timedelta-dtype Series; df.cumprod() on a timedelta column; arr._accumulate('cumprod').

Common situations: Generic accumulation suites applied across mixed dtypes; refactoring a numeric column to timedelta and forgetting cumprod breaks.

Related errors


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

Appendix: source

Thrown at pandas/core/arrays/timedeltas.py:444

            (), {"dtype": dtype, "out": out, "keepdims": keepdims}, fname="std"
        )

        result = nanops.nanstd(self._ndarray, axis=axis, skipna=skipna, ddof=ddof)
        if axis is None or self.ndim == 1:
            return self._box_func(result)
        return self._from_backing_data(result)

    # ----------------------------------------------------------------
    # Accumulations

    def _accumulate(self, name: str, *, skipna: bool = True, **kwargs):
        if name == "cumsum":
            op = getattr(datetimelike_accumulations, name)
            result = op(self._ndarray.copy(), skipna=skipna, **kwargs)

            return type(self)._simple_new(result, dtype=self.dtype)
        elif name == "cumprod":
            raise TypeError("cumprod not supported for Timedelta.")

        else:
            return super()._accumulate(name, skipna=skipna, **kwargs)

    # ----------------------------------------------------------------
    # Rendering Methods

    def _formatter(self, boxed: bool = False):
        from pandas.io.formats.format import get_format_timedelta64

        return get_format_timedelta64(self, box=True)

    def _format_native_types(
        self, *, na_rep: str | float = "NaT", date_format=None, **kwargs
    ) -> npt.NDArray[np.object_]:
        from pandas.io.formats.format import get_format_timedelta64

        # Relies on TimeDelta._repr_base

View on GitHub (pinned to 3b7651241d)