Python拟合指数衰减函数得到直线的问题排查
问题:拟合指数衰减函数却得到直线
我用Python对数据进行最优拟合,尝试拟合指数衰减函数,但结果却得到一条直线。数据存储在GitHub仓库DeAngelo-neutrino/artie的pythonprogram文件夹中,可忽略其中图片。
核心代码流程如下:
- 导入库并读取数据
import matplotlib.pyplot as plt import numpy as np import pandas as pd import os import math import sys from scipy.interpolate import UnivariateSpline from scipy.optimize import curve_fit # 原代码遗漏该关键导入 np.set_printoptions(threshold=sys.maxsize) pd.set_option('display.max_columns', None) pd.set_option('display.max_rows', None) os.chdir("/Users/dwooley/Desktop/Python_programs/") # 读取数据列 time_argon = np.genfromtxt("log_all_chan_5_10-14_17_44.txt",skip_header=9, delimiter=",", usecols=(0)) target_top = np.genfromtxt("log_all_chan_5_10-14_17_44.txt",skip_header=9, delimiter=",", usecols=(1)) target_side = np.genfromtxt("log_all_chan_5_10-14_17_44.txt",skip_header=9, delimiter=",", usecols=(2)) target_bottom = np.genfromtxt("log_all_chan_5_10-14_17_44.txt",skip_header=9, delimiter=",", usecols=(3)) front_plate= np.genfromtxt("log_all_chan_5_10-14_17_44.txt",skip_header=9, delimiter=",", usecols=(4)) N2_level= np.genfromtxt("log_all_chan_5_10-14_17_44.txt",skip_header=9, delimiter=",", usecols=(9))
- 创建DataFrame并计算滚动平均
df = pd.read_csv("log_all_chan_5_10-14_17_44.txt", skiprows=9, sep=',' ) window_size = 900 time_column = df['Time (s)'] N2_level_dataseries = df['N2 Level'] N2_average = N2_level_dataseries.rolling(window = window_size).mean()
- 体积计算(省略无关细节)
# 此处为体积计算代码,略去具体实现 # ... df['volume(Argon)'] = v_h_0+(df['test']) + twice_length*full_integration volume_function_as_height = df['volume(Argon)']
- 筛选数据并拟合
lower_parsed_data = 8000 upper_parsed_data = 10000 data_we_use = volume_function_as_height.iloc[lower_parsed_data:upper_parsed_data] # 补充原代码缺失的时间数据切片 parsed_time_average = time_column.iloc[lower_parsed_data:upper_parsed_data] def exponential_decay(x, A, B, C): return A* np.exp(-B * x) + C x_data = parsed_time_average y_data = data_we_use initial_guess = [max(y_data), 1, min(y_data)] # 执行拟合 popt, pcov = curve_fit(exponential_decay, x_data, y_data, p0=initial_guess) A_opt, B_opt, C_opt = popt y_fit = exponential_decay(x_data, *popt) # 绘图 plt.figure(figsize=(10, 6)) plt.plot(x_data, y_data, 'g-',label='数据') plt.plot(x_data, y_fit, label='指数衰减拟合', color='blue') plt.xlabel('时间(s)') plt.ylabel('氩气体积(inches³)') plt.title('指数衰减拟合结果') plt.legend() plt.show()
拟合结果为直线而非预期曲线,以下是解决思路:
修正初始猜测值:初始猜测的B值设为1过大(时间以秒为单位时,衰减常数通常很小),建议改为贴合数据量级的数值,比如:
initial_guess = [max(y_data)-min(y_data), 0.0001, min(y_data)]确保x与y数据完全匹配:原代码未定义
parsed_time_average,必须补充时间数据的切片代码,保证时间序列和体积序列的索引完全对应,否则拟合逻辑会失效。添加拟合参数边界:强制B为正数(避免B=0导致直线拟合),在
curve_fit中加入边界限制:popt, pcov = curve_fit(exponential_decay, x_data, y_data, p0=initial_guess, bounds=([0, 1e-6, 0], [np.inf, np.inf, np.inf]))检查滚动平均的影响:窗口大小900可能过度平滑数据,掩盖了衰减趋势。尝试减小窗口(如100)或直接使用原始
N2_level_dataseries计算,观察数据的真实变化趋势。验证数据区间:当前选择的8000-10000行数据可能已处于衰减末期,接近平稳状态,自然呈现线性。可以尝试选择更早的区间(如3000-7000行),看是否存在明显的衰减特征。
内容的提问来源于stack exchange,提问作者Deangelo Wooley
相关产品推荐
相关产品推荐

