我有一组N个样本(N~10000到100000):
(y_i, P_i)
他们采样未知函数:
y = f(P)
就我而言,P是一组n_p参数,n_p通常大约为10。
我的目的是使用样本找到2阶多项式,它近似于我最大的未知函数。典型的结果是最佳拟合多项式的(n_p + 1)+(n_p + 1)* n_p / 2个系数。
但是,我想以下列形式获得解决方案:
f(P) = (P-mu)*(C^-1)*(P-mu)^T + K
具有维数为n_p的矢量,C a(n_p X n_p)对称矩阵,并且K为常数。这些mu,C和K是我想要获得的。
Python生态系统中是否存在标准实现和/或有效的方法?
提前致谢!
修改: 这是一个典型的设置,我创建假样本(P和Y),并且只使用它们,我想恢复原始的mu,C和K:
import numpy as np
n_p = 3
N = 15
# Generate the "mu" we'll try to recover
mu = np.random.rand(n_p)
# Generate the "C" we'll try to recover
tmp = np.random.rand(n_p,n_p)
C = np.dot(tmp, tmp.T)
# Generate the "K" we'll try to recover
K = np.random.rand()
# Generate the samples
P = np.random.rand(n_p,N)
Y = np.array([np.dot(np.dot((P[:,i]-mu),np.linalg.inv(C)),(P[:,i]-mu))+K for i in range(N)])
答案 0 :(得分:0)
这就是你要找的东西吗?我并非100%确定它对您的用例是准确的(我不知道当您对2阶多项式拟合时可以施加的其他约束),但它应该尝试找到一个U,A(你称之为C),以及最小化最小二乘误差的K.
import numpy as np
from scipy import optimize
import matplotlib.pyplot as plt
samples = 100
num_params = 20
y = np.random.rand(samples)
p = np.random.rand(samples, num_params)
def my_func(params):
u = params[0:num_params]
u = np.expand_dims(u, axis=1)
a = params[num_params:-1]
k = params[-1]
a = a.reshape(num_params, num_params)
a_inv = np.linalg.inv(a)
shifted_p = p - np.transpose(u)
mult_with_a_inv = np.dot(shifted_p, a_inv)
mat_mult_vec = np.einsum('ij,ji->i', mult_with_a_inv, np.transpose(shifted_p))
return_val = y - k - mat_mult_vec
return sum(return_val**2)
guess = np.random.rand(num_params+num_params**2+1)
new_params = optimize.fmin_cg(my_func, guess)
new_u = new_params[0:num_params]
new_a = new_params[num_params:-1]
new_a = new_a.reshape(num_params, num_params)
new_k = new_params[-1]
original_y, = plt.plot(np.arange(samples), y)
new_y, = plt.plot(np.arange(samples), np.einsum('ij,ji->i', np.dot(p-np.transpose(new_u),
np.linalg.inv(new_a)),
np.transpose(p-np.transpose(new_u))
) + new_k)
plt.legend([original_y, new_y], ['Original Y', 'Newly Fitted Y'])
plt.show()
这可能是一种更加数学上合理的方法,但希望这至少有帮助。
编辑:刚刚注意到我弄乱了k的标志。我还需要提高参数数量。这似乎工作得非常好。我几乎完全恢复了原来的噪音。
同时添加样本输出。