2017-01-28 15 views
1

ここでは例として標準的なmatplotlibのsurfaceplotを使用しています。3D表面/等高線の投影された最小値と最大値のマーク

from mpl_toolkits.mplot3d import axes3d 
import matplotlib.pyplot as plt 
from matplotlib import cm 

fig = plt.figure() 
ax = fig.gca(projection='3d') 
X, Y, Z = axes3d.get_test_data(0.05) 
ax.plot_surface(X, Y, Z, rstride=8, cstride=8, alpha=0.3) 
cset = ax.contour(X, Y, Z, zdir='z', offset=-100, cmap=cm.coolwarm) 
cset = ax.contour(X, Y, Z, zdir='x', offset=-40, cmap=cm.coolwarm) 
cset = ax.contour(X, Y, Z, zdir='y', offset=40, cmap=cm.coolwarm) 

ax.set_xlabel('X') 
ax.set_xlim(-40, 40) 
ax.set_ylabel('Y') 
ax.set_ylim(-40, 40) 
ax.set_zlabel('Z') 
ax.set_zlim(-100, 100)][1]][1] 

Example plot with two extrema

Iは、輪郭上のそれぞれの位置の「X」を用いて表面の2つの極値をマークしたいです。 これはどのように達成できますか?

私が試した:

max_column = np.argmax(np.max(Z, axis=0)) 
max_row = np.argmax(np.max(Z, axis=1)) 

min_column = np.argmin(np.min(Z, axis=0)) 
min_row = np.argmin(np.min(Z, axis=1)) 

target = [max_row,max_column,0] 


ax.plot([target[0]],[target[1]],[0],'r',marker = u'X',markersize = 8) 

私は何とか投影座標を必要とすると思います。

さらに、極値がある2D平面上に線でヘアラインクロスを描きたいと思います。

答えて

0

まず、Z配列の最小値と最大値に対応するポイントを調べる必要があります。
これらの点をプロットすることができます。座標の1つを輪郭からそれぞれのoffsetの値に設定すると、投影されます。

from mpl_toolkits.mplot3d import axes3d 
import matplotlib.pyplot as plt 
from matplotlib import cm 
import numpy as np 

fig = plt.figure() 
ax = fig.gca(projection='3d') 
X, Y, Z = axes3d.get_test_data(0.05) 
ax.plot_surface(X, Y, Z, rstride=8, cstride=8, alpha=0.3) 
cset = ax.contour(X, Y, Z, zdir='z', offset=-100, cmap=cm.coolwarm) 
cset = ax.contour(X, Y, Z, zdir='x', offset=-40, cmap=cm.coolwarm) 
cset = ax.contour(X, Y, Z, zdir='y', offset=40, cmap=cm.coolwarm) 

ax.set_xlabel('X') 
ax.set_xlim(-40, 40) 
ax.set_ylabel('Y') 
ax.set_ylim(-40, 40) 
ax.set_zlabel('Z') 
ax.set_zlim(-100, 100) 

# calc index of min/max Z value 
xmin, ymin = np.unravel_index(np.argmin(Z), Z.shape) 
xmax, ymax = np.unravel_index(np.argmax(Z), Z.shape) 

# min max points in 3D space (x,y,z) 
mi = (X[xmin,ymin], Y[xmin,ymin], Z.min()) 
ma = (X[xmax, ymax], Y[xmax, ymax], Z.max()) 

# Arrays for plotting, 
# first row for points in xplane, last row for points in 3D space 
Ami = np.array([mi]*4) 
Ama = np.array([ma]*4) 
for i, v in enumerate([-40,40,-100]): 
    Ami[i,i] = v 
    Ama[i,i] = v 

#plot points. 
ax.plot(Ami[:,0], Ami[:,1], Ami[:,2], marker="o", ls="", c=cm.coolwarm(0.)) 
ax.plot(Ama[:,0], Ama[:,1], Ama[:,2], marker="o", ls="", c=cm.coolwarm(1.)) 

ax.view_init(azim=-45, elev=19) 
plt.savefig(__file__+".png") 
plt.show() 

enter image description here