将 Pandas DataFrame 传递给 Scipy.optimize.curve_fit
Pass Pandas DataFrame to Scipy.optimize.curve_fit
我想知道使用 Scipy 来适应 Pandas DataFrame 列的最佳方法。如果我有一个包含列(A
、B
、C
、D
和 Z_real
的数据 table(Pandas DataFrame) ) 其中 Z 取决于 A、B、C 和 D,我想拟合每个 DataFrame 行(系列)的函数,该函数对 Z (Z_pred
) 进行预测。
要拟合的每个函数的签名是
func(series, param_1, param_2...)
其中series是DataFrame每一行对应的Pandas系列。我使用 Pandas 系列,以便不同的功能可以使用不同的列组合。
我尝试使用
将DataFrame传递给scipy.optimize.curve_fit
curve_fit(func, table, table.loc[:, 'Z_real'])
但出于某种原因,每个 func 实例都将整个数据table 作为其第一个参数而不是每行的 Series 传递。我也尝试过将 DataFrame 转换为 Series 对象列表,但这导致我的函数被传递了一个 Numpy 数组(我认为是因为 Scipy 执行了从 Series 列表到 Numpy 数组的转换,而 Numpy 数组不t 保留 Pandas 系列对象)。
您对 curve_fit
的调用不正确。来自 the documentation:
xdata : An M-length sequence or an (k,M)-shaped array for functions with k predictors.
The independent variable where the data is measured.
ydata : M-length sequence
The dependent data — nominally f(xdata, ...)
在这种情况下,您的 自变量 xdata
是 A 到 D 列,即 table[['A', 'B', 'C', 'D']]
,以及您的 因变量 ydata
是 table['Z_real']
.
还要注意xdata
应该是一个(k, M)数组,其中k是预测变量的个数变量(即列)和 M 是观察数(即行)。因此,您应该转置输入数据帧,使其成为 (4, M) 而不是 (M, 4),即 table[['A', 'B', 'C', 'D']].T
.
对 curve_fit
的整个调用可能如下所示:
curve_fit(func, table[['A', 'B', 'C', 'D']].T, table['Z_real'])
这是一个显示多元线性回归的完整示例:
import numpy as np
import pandas as pd
from scipy.optimize import curve_fit
X = np.random.randn(100, 4) # independent variables
m = np.random.randn(4) # known coefficients
y = X.dot(m) # dependent variable
df = pd.DataFrame(np.hstack((X, y[:, None])),
columns=['A', 'B', 'C', 'D', 'Z_real'])
def func(X, *params):
return np.hstack(params).dot(X)
popt, pcov = curve_fit(func, df[['A', 'B', 'C', 'D']].T, df['Z_real'],
p0=np.random.randn(4))
print(np.allclose(popt, m))
# True
我想知道使用 Scipy 来适应 Pandas DataFrame 列的最佳方法。如果我有一个包含列(A
、B
、C
、D
和 Z_real
的数据 table(Pandas DataFrame) ) 其中 Z 取决于 A、B、C 和 D,我想拟合每个 DataFrame 行(系列)的函数,该函数对 Z (Z_pred
) 进行预测。
要拟合的每个函数的签名是
func(series, param_1, param_2...)
其中series是DataFrame每一行对应的Pandas系列。我使用 Pandas 系列,以便不同的功能可以使用不同的列组合。
我尝试使用
将DataFrame传递给scipy.optimize.curve_fit
curve_fit(func, table, table.loc[:, 'Z_real'])
但出于某种原因,每个 func 实例都将整个数据table 作为其第一个参数而不是每行的 Series 传递。我也尝试过将 DataFrame 转换为 Series 对象列表,但这导致我的函数被传递了一个 Numpy 数组(我认为是因为 Scipy 执行了从 Series 列表到 Numpy 数组的转换,而 Numpy 数组不t 保留 Pandas 系列对象)。
您对 curve_fit
的调用不正确。来自 the documentation:
xdata : An M-length sequence or an (k,M)-shaped array for functions with k predictors.
The independent variable where the data is measured.
ydata : M-length sequence
The dependent data — nominally f(xdata, ...)
在这种情况下,您的 自变量 xdata
是 A 到 D 列,即 table[['A', 'B', 'C', 'D']]
,以及您的 因变量 ydata
是 table['Z_real']
.
还要注意xdata
应该是一个(k, M)数组,其中k是预测变量的个数变量(即列)和 M 是观察数(即行)。因此,您应该转置输入数据帧,使其成为 (4, M) 而不是 (M, 4),即 table[['A', 'B', 'C', 'D']].T
.
对 curve_fit
的整个调用可能如下所示:
curve_fit(func, table[['A', 'B', 'C', 'D']].T, table['Z_real'])
这是一个显示多元线性回归的完整示例:
import numpy as np
import pandas as pd
from scipy.optimize import curve_fit
X = np.random.randn(100, 4) # independent variables
m = np.random.randn(4) # known coefficients
y = X.dot(m) # dependent variable
df = pd.DataFrame(np.hstack((X, y[:, None])),
columns=['A', 'B', 'C', 'D', 'Z_real'])
def func(X, *params):
return np.hstack(params).dot(X)
popt, pcov = curve_fit(func, df[['A', 'B', 'C', 'D']].T, df['Z_real'],
p0=np.random.randn(4))
print(np.allclose(popt, m))
# True