Во-первых, ваша программа работает медленно, потому что вы выполняете много ненужной работы по созданию N
. Вы строите список размером 70 МБ по несколько байтов за раз (256*256*256=16 777 216 добавлений!). Лучший (более быстрый, эффективный с точки зрения памяти) способ построить p
- использовать широковещательную передачу массива numpy, а затем повторно использовать p
для создания N
:
import numpy as np
a = np.arange(256)
p = a[:,np.newaxis,np.newaxis] * a[np.newaxis,:,np.newaxis] * a[np.newaxis,np.newaxis,:]
N = p.flatten()
Во-вторых, что более важно, вы неправильно используете plot_surface(). Согласно документам, X, Y и Z должны быть 2D массивы. X и Y закладывают 2D-сетку, а Z обеспечивает «высоту» для каждой точки этой 2D-сетки. Если вы хотите вручную установить цвет лица, он также должен быть двумерным массивом. Вы должны посмотреть пример в документации для рабочего примера.
РЕДАКТИРОВАТЬ:
Я не уверен, как должен выглядеть ваш график, поэтому давайте пройдемся по MPL демо.
Сделайте необходимые импорты и создайте объект оси (ваш делает это правильно):
from mpl_toolkits.mplot3d import Axes3D
from matplotlib import cm
from matplotlib.ticker import LinearLocator, FormatStrFormatter
import matplotlib.pyplot as plt
import numpy as np
fig = plt.figure()
ax = fig.gca(projection='3d')
Затем создайте сетку X/Y и соответствующую Z. В вашей программе X, Y и Z являются одномерными. Они описывают линию в трехмерном пространстве, а не поверхность.
X = np.arange(-5, 5, 0.25)
Y = np.arange(-5, 5, 0.25)
X, Y = np.meshgrid(X, Y) # <-- returns a 2D grid from initial 1D arrays
R = np.sqrt(X**2 + Y**2)
Z = np.sin(R)
Давайте сначала построим простейшую возможную вещь. Без цветов, сглаживания по умолчанию, линий и т. д.
surf = ax.plot_surface(X, Y, Z, rstride=1, cstride=1)
plt.show()
Теперь добавьте цвета. Обратите внимание, что цвет исходит из компонента Z.
surf = ax.plot_surface(X, Y, Z, rstride=1, cstride=1, cmap=cm.jet)
plt.show()
Теперь вручную управляйте цветами (вдохновение для MPL).
colortuple = ('y', 'k') # only use two colors: yellow and black
xlen, ylen = X.shape # get length of
colors = np.empty(X.shape, dtype=str) # make a 2D array of strings
for i in range(xlen):
for j in range(ylen):
index = (i + j) % 2 # alternating 0's and 1's
colors[i,j] = colortuple[index]
surf = ax.plot_surface(X, Y, Z, rstride=1, cstride=1,
facecolors=colors)
Если вы хотите раскрасить на основе какой-либо другой метрики, вы можете создать свою собственную палитру. Есть много ответов на вопросы о том, как это сделать.
Редактировать 2:
Цвета также могут быть указаны как последовательности RGB. Для чего-то вроде вашего красного на X, зеленого на описании Y вы можете сделать это:
xlen, ylen = X.shape
colors = np.zeros((xlen,ylen,3))
jspan = np.linspace(0., 1., ylen)
ispan = np.linspace(0., 1., xlen)
for i in range(xlen):
colors[i,:,0] = jspan
for j in range(ylen):
colors[:,j,1] = ispan
surf = ax.plot_surface(X, Y, Z, rstride=1, cstride=1, facecolors=colors,)
person
matt
schedule
27.01.2012