You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

使用D3绘制趋势线问题:实际与预测数据趋势线异常

Fixing the Misaligned Forecast Trendline in Your D3.js Chart

Hey there, I spotted the issue causing your forecast trendline to draw incorrectly—it’s all in how you’re calculating the y-values for the trendline endpoints! Let’s break this down and fix it.

The Root Problem

In your code, you’re calculating y1 and y2 using logic that only works by coincidence for your actual data:

y1 = leastSquaresCoeff[0] + leastSquaresCoeff[1]; // Wrong! Should use x1
y2 = leastSquaresCoeff[0] * xSeries.length + leastSquaresCoeff[1]; // Wrong! Should use x2

For your actual data, x1 happens to be 1, so m*1 + b equals m + b—that’s why it works. And xSeries.length matches x2 (32), so m*32 + b is correct. But for forecast data, x1 starts at 33 and x2 is 64, while xSeries.length stays at 32—this misalignment breaks the trendline calculation entirely.

The Fix

You need to plug the actual x1 and x2 values directly into your least squares regression equation (y = mx + b, where leastSquaresCoeff[0] is the slope m and leastSquaresCoeff[1] is the intercept b). Here’s the corrected code section:

// get the x and y values for least squares
xSeries = d3.range(d3.min(actualData, function(d) { return d.items[columns.indexOf("Week")]; }), d3.max(actualData, function(d) { return d.items[columns.indexOf("Week")]; }) + 1);
ySeries = actualData.map(function(d) { return parseFloat(d.items[columns.indexOf("Measure")]) });
leastSquaresCoeff = leastSquares(xSeries, ySeries);

// apply the results of the least squares regression (CORRECTED!)
x1 = actualData[0].items[columns.indexOf("Week")];
y1 = leastSquaresCoeff[0] * x1 + leastSquaresCoeff[1]; // Use x1 in the regression formula
x2 = actualData[actualData.length - 1].items[columns.indexOf("Week")];
y2 = leastSquaresCoeff[0] * x2 + leastSquaresCoeff[1]; // Use x2 in the regression formula

trendData = [ [x1, y1, x2, y2] ];
trendline = svg.selectAll(".trendline")
 .data(trendData).enter()
 .append("line")
 .attr("class", "trendline")
 .style("stroke-dasharray", ("3, 3"))
 .attr("x1", function(d) { return x(d[0]); })
 .attr("y1", function(d) { return y(d[1]); })
 .attr("x2", function(d) { return x(d[2]); })
 .attr("y2", function(d) { return y(d[3]); })
 .attr("stroke", "#319455")
 .attr("stroke-width", 1);

Why This Works

By using the actual week values (x1 and x2) in the regression equation, you ensure the trendline endpoints are calculated correctly regardless of whether you’re working with actual or forecast data. Now when you toggle the time config parameter between actual and forecast, both trendlines will align perfectly with their respective datasets.

内容的提问来源于stack exchange,提问作者CStreet

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.14 06:57:35