Skip to content

Extra factors (regressors) ​

Sometimes you know something that helps explain your data: the temperature, how much you spent on ads, whether a promotion was running. Add these as regressors.

Verified against Python Prophet

Regressors match Python Prophet 1.4.0 on all three trend types. The seasonality, events and regressors benchmarks show every case side by side.

ts
import { Effect } from "effect";
import { fit, getRegressorCoefficients, predict, prophetFittingBackendLayer } from "effect-prophet";

const date = (day: number) => new Date(Date.UTC(2025, 0, 1 + day)).toISOString();

const temperature = (day: number) => 15 + 10 * Math.sin((2 * Math.PI * day) / 365);

// Ice cream sales follow the temperature: about 4 extra sales per degree.
const history = Array.from({ length: 200 }, (_, day) => ({
  timestamp: date(day),
  value: 40 + 4 * temperature(day),
  regressors: { temperature: temperature(day) },
}));

const model = fit(history, {
  regressors: [{ name: "temperature" }],
});

// You must supply the regressor for every future row, e.g. from a weather forecast.
const future = Array.from({ length: 3 }, (_, offset) => ({
  timestamp: date(200 + offset),
  regressors: { temperature: 30 },
}));

const result = await Effect.runPromise(
  Effect.gen(function* () {
    const fitted = yield* model;

    return { fitted, forecast: yield* predict(fitted, future) };
  }).pipe(Effect.provide(prophetFittingBackendLayer)),
);

for (const coefficient of getRegressorCoefficients(result.fitted)) {
  console.log(coefficient.name, coefficient.mode, coefficient.coefficient.toFixed(2));
}

console.log(result.forecast.map((row) => row.value.toFixed(1)).join(", "));
txt
temperature additive 4.00
160.0, 160.0, 160.0

The model learned the real relationship: 4 extra sales for every degree.

Things to know ​

  • Every row needs every regressor, in both the history and the future rows. If you don't know the future value, you need your own forecast of it, such as a weather forecast.
  • Regressors are numbers. Use 1 and 0 for yes/no factors.
  • getRegressorCoefficients(model) shows what the model learned: how much the forecast changes per one unit of each regressor, in your data's units.
  • Options for each regressor:
OptionDefaultMeaning
priorScale10Lower values keep the effect small unless the data clearly supports it
mode"additive""multiplicative" makes the effect a percentage of the trend
standardization"auto"Rescales the values internally for a stable fit. "auto" leaves yes/no (0/1) values alone.

Inspired by Prophet from Meta. Not affiliated with Meta.