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

使用lmfit与scipy.curve_fit拟合对数曲线失败求助

投票数与认可指数的对数曲线拟合问题排查

问题背景

使用《终极电影统计数据集》分析时,发现投票数(x轴)与认可指数(y轴)存在对数关系,但用scipy.curve_fit和lmfit拟合时,要么得到错误的拟合曲线,要么抛出真值错误。代入在线工具得到的拟合方程y = 0.986203*np.log(12.6695*x + 64567.3) - 8.30291作为初始参数仍无效。

原代码中的核心问题

  1. 未定义变量:代码中使用newdf但未初始化,应替换为读取后的df
  2. 模型函数定义错误:
    • scipy.curve_fit使用的logfunction仅包含a*np.log(b*x),与实际需要的带常数偏移的对数模型不符
    • lmfit的函数未将拟合参数作为输入参数,而是直接引用全局变量,导致拟合时无法识别参数
  3. 语法错误:第二次lmfit尝试中,函数返回语句写为return y = ...,属于非法赋值语法
  4. 数据未预处理:未检查/过滤投票数为0的行,会导致np.log(0)引发数值错误
  5. 初始参数设置不合理:部分拟合尝试未提供接近真实值的初始参数,导致优化算法收敛失败

修正后的代码示例

1. 数据预处理与基础准备

import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
from scipy.optimize import curve_fit
from lmfit import Model

# 读取数据并预处理
df = pd.read_csv('movie_statistic_dataset.csv')
# 替换未定义的newdf为df,过滤投票数为0的行避免log报错
data = df[['movie_numerOfVotes','approval_Index']].query('movie_numerOfVotes > 0').reset_index(drop=True)
data.columns = ['Votes','Approval']

X = data['Votes'].values
Y = data['Approval'].values

2. 使用scipy.curve_fit拟合

# 定义与在线工具一致的对数模型
def log_model(x, a, b, c, d):
    return a * np.log(b * x + c) - d

# 传入在线工具得到的初始参数,提升拟合收敛效率
initial_params = [0.986, 12.67, 64567, 8.303]
popt, pcov = curve_fit(log_model, X, Y, p0=initial_params)

# 生成拟合预测值
y_pred = log_model(X, *popt)

# 可视化对比
plt.scatter(X, Y, label='原始数据', alpha=0.5)
plt.plot(X, y_pred, color='red', label='拟合曲线')
plt.xlabel('投票数')
plt.ylabel('认可指数')
plt.legend()
plt.show()

print(f"拟合参数:a={popt[0]:.4f}, b={popt[1]:.4f}, c={popt[2]:.0f}, d={popt[3]:.4f}")

3. 使用lmfit拟合

# 正确定义模型函数(参数作为输入)
def lm_log_model(x, a, b, c, d):
    return a * np.log(b * x + c) - d

# 创建模型并设置初始参数
mod = Model(lm_log_model)
params = mod.make_params(a=0.986, b=12.67, c=64567, d=8.303)

# 执行拟合
result = mod.fit(Y, params=params, x=X)

# 输出拟合报告
print(result.fit_report())

# 可视化
plt.scatter(X, Y, label='原始数据', alpha=0.5)
plt.plot(X, result.best_fit, color='green', label='LM拟合曲线')
plt.xlabel('投票数')
plt.ylabel('认可指数')
plt.legend()
plt.show()

关键注意事项

  • 初始参数的重要性:对数模型属于非线性拟合,初始参数接近真实值能大幅提升算法收敛成功率
  • 数据校验:必须确保输入x(投票数)无0值或负数,避免对数运算抛出数值错误
  • 函数定义规范:lmfit要求模型函数将所有待拟合参数作为输入参数,不能使用全局变量

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.29 00:47:47