numpy 更新scipy.stats.multivariate_normal的协方差时的属性错误

z6psavjg  于 12个月前  发布在  其他
关注(0)|答案(1)|浏览(97)

我想顺序更新多元高斯分布的协方差矩阵,但得到一个AttributeError。下面是一段简单的代码来重现错误:

import numpy as np
from scipy.stats import multivariate_normal
# Initial mean 
init_pose = np.array([0, 0, 0]).T

# Multi-variate Gaussian 
belief = multivariate_normal(mean=init_pose, cov=np.diag([1e-10, 1e-10, 1e-10])) 
print(belief.mean, belief.cov)

# Update mean and covariance 
belief.mean = np.array([10, 20, 30]).T
belief.cov = np.diag([1, 2, 3])

字符串
错误消息包括:

AttributeError                            Traceback (most recent call last)
Cell In[42], line 7
      5 print(belief.mean, belief.cov)
      6 belief.mean = np.array([10, 20, 30]).T
----> 7 belief.cov = np.diag([1, 2, 3])
      8 print(belief.mean, belief.cov)

AttributeError: can't set attribute


我使用belief.__dict__检查了变量belief的属性,结果如下:

{'_dist': <scipy.stats._multivariate.multivariate_normal_gen object at 0x2b84d81cfc10>,
 'dim': 3, 'mean': array([0., 0., 0.]), 
'cov_object': <scipy.stats._covariance.CovViaPSD object at 0x2b84d81cfbe0>, 
'allow_singular': False, 'maxpts': 3000000, 'abseps': 1e-05, 'releps': 1e-05}


如错误所示,变量没有cov属性,而是有cov_object。有没有办法使用numpy数组更新协方差?

pkln4tw6

pkln4tw61#

现有的基础设施并不支持更新协方差矩阵。cov是一个只读属性,正如您在源代码中看到的那样。(尽管没有文档记录,但这是多变量分布的许多known issues之一。)
你可以 *(虽然官方不支持)更新你找到的cov_object属性。如果你使用stats.Covariance,我推荐,这可能看起来像:

import numpy as np
from scipy.stats import multivariate_normal, Covariance

x = [1, 1, 1]

# Initial mean and covariance
init_pose = np.array([0, 0, 0]).T
cov = Covariance.from_diagonal(np.array([1, 2, 3]))

# Multi-variate Gaussian 
belief = multivariate_normal(mean=init_pose, cov=cov) 
belief.pdf(x)  # 0.01036457019516129

# Update covariance
cov = Covariance.from_diagonal(np.array([2, 4, 6]))
belief.cov_object = cov
belief.pdf(x)  # 0.005795060058469202
# same as
# multivariate_normal(mean=init_pose, cov=cov).pdf(x)

字符串
只要你的新meancov_object不违反你可以从_process_parameters_Covariance推断出的条件(基本上只是一致的维数),我希望它能正确工作。如果你改变meancov_object来表示不同维数的多元正态,你还需要相应地更新dim属性。
在评论中,你写道:
但是,我不知道如何定义非对角协方差矩阵。
Covariance还有其他几个定义协方差矩阵的选项。SciPy文档似乎有证书问题ATM,但你会发现其他方法,如from_precisionfrom_choleskyfrom_eigendecomposition,可以用于更一般的协方差矩阵。
那么,这是否意味着一个值不能以这种方式设置为协方差,因为协方差是一个属性而不是一个属性?
这是因为它是一个使用@property修饰符创建的只读属性;它不是在__init__方法(如self.cov = cov)中定义的普通属性。

相关问题