matplotlib 在contour中使用zdir的问题

nwlls2ji  于 2023-10-24  发布在  其他
关注(0)|答案(1)|浏览(108)

我尝试使用matplotlib从3D散点图绘制2D切片,遇到了zdir参数问题。下面是我的代码:

import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import axes3d
from scipy.stats import multivariate_normal

mean = np.array([0, 0, 0])
covariance_matrix = np.array([[1, 0.5, 0.2],
                               [0.5, 1, 0.3],
                               [0.2, 0.3, 1]])

x1=np.linspace(-3, 3, 50)
x, y, z = np.meshgrid(x1,x1,x1)
pos = np.column_stack((x.ravel(), y.ravel(), z.ravel()))
pdf_values = multivariate_normal.pdf(pos, mean=mean, cov=covariance_matrix)
pdf_values = pdf_values.reshape(50, 50, 50)
fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')
x_flat, y_flat, z_flat = x.flatten(), y.flatten(), z.flatten()
pdf_flat = pdf_values.flatten()
threshold=0.03
inside_sphere = pdf_flat > threshold
from matplotlib import cm
ax.scatter(x_flat[inside_sphere], y_flat[inside_sphere], z_flat[inside_sphere], c=pdf_flat[inside_sphere], marker='.',s=1)

ax.contour(X=x[:,:,25], Y=y[:,:,25], Z=pdf_values[:,:,25], zdir='z',offset=-1.5 , cmap=cm.coolwarm)
#Problems begin when changing zdir to a non-z argument
ax.contour(X=x[25,:,:], Y=z[25,:,:], Z=pdf_values[25,:,:], zdir='y', cmap=cm.coolwarm)

plt.show()

这将生成以下图像

但是Y投影在哪里呢?如果你注解掉另外两行,你会得到这样的结果:

zdir参数更改为“z”会变成一个更容易识别的等高线图。为什么?

sg24os4d

sg24os4d1#

解决方案

如果你想在y-axis上显示图的轮廓,那么你应该将ax.contour(...)中的Y参数更改为pdf_values数组。保持XZ参数分别等于xz数组。这也可以应用于其他轴。

您的代码适用于zdir='z'的情况,因为您已经设置了Z=pdf_values[...]。只需将此方法应用于其他轴!
注:将轴限制设置为等于轮廓函数中的偏移量,会使轮廓看起来位于图形的“墙壁”上。

代码

import numpy as np
import matplotlib.pyplot as plt
from mpl_toolkits.mplot3d import axes3d
from scipy.stats import multivariate_normal

mean = np.array([0, 0, 0])
covariance_matrix = np.array([[1, 0.5, 0.2],
                               [0.5, 1, 0.3],
                               [0.2, 0.3, 1]])

x1=np.linspace(-3, 3, 50)
x, y, z = np.meshgrid(x1,x1,x1)
pos = np.column_stack((x.ravel(), y.ravel(), z.ravel()))
pdf_values = multivariate_normal.pdf(pos, mean=mean, cov=covariance_matrix)
pdf_values = pdf_values.reshape(50, 50, 50)
fig = plt.figure()
ax = fig.add_subplot(111, projection='3d')
x_flat, y_flat, z_flat = x.flatten(), y.flatten(), z.flatten()
pdf_flat = pdf_values.flatten()
threshold=0.03
inside_sphere = pdf_flat > threshold
from matplotlib import cm
ax.scatter(x_flat[inside_sphere], y_flat[inside_sphere], z_flat[inside_sphere], c=pdf_flat[inside_sphere], marker='.',s=1)

ax.contour(X=x[:,:,25], Y=y[:,:,25], Z=pdf_values[:,:,25], zdir='z',offset=-2.5 , cmap=cm.coolwarm)

###### EDITS START HERE ######
#Change which axis is set to the 'pdf_values' array
ax.contour(X=x[25,:,:], Y=pdf_values[25,:,:], Z=z[25,:,:], offset=2.5, zdir='y', cmap=cm.coolwarm)
ax.contour(X=pdf_values[:,25,:], Y=y[:,25,:], Z=z[:,25,:], offset=-2.5, zdir='x', cmap=cm.coolwarm)

# Set axes limits so that contour appears on the figure 'wall'
ax.set_xlim(-2.5,2.5)
ax.set_ylim(-2.5,2.5)
ax.set_zlim(-2.5,2.5)
######  EDITS END HERE  ######

plt.show()

相关问题