由于循环而使用np.meshgrid绘制3d图时发生错误

时间:2019-05-22 06:14:10

标签: python numpy matplotlib mplot3d

我有一个形式为

的函数
<div class="container">
  Question:
  <br>

  <textarea rows="5" cols="50" name="description" placeholder="Enter a question">
         </textarea>
  <br>

  <select name="choice" id="choice" onchange="selectorchecker()">
    <option value="">Select choices</option>
    <option value="checkbox">Checkbox</option>
    <option value="radiobtn">Radio Button</option>
  </select>
</div>

<button id="addQues">Add Question</button>

<div style="display:none;" id="chkbox_choice">
  <table id="dataTable" width="350px">
    <tr>
      <td><input type="checkbox" name="check" /></td>
      <td>
        <INPUT type="text" /> </td>
    </tr>
  </table>

  <input type="button" value="Add choices" onclick="addRow('dataTable')" />

  <input type="button" value="Delete choices" onclick="deleteRow('dataTable')" />
</div>


<div style="display:none;" id="rdbtn_choice">
  <table id="dataTable" width="350px">
    <tr>
      <td><input type="radio" name="radio" /></td>
      <td>
        <INPUT type="text" /> </td>
    </tr>
  </table>

  <input type="button" value="Add choices" onclick="addRow('dataTable')" />

  <input type="button" value="Delete choices" onclick="deleteRow('dataTable')" />
</div>

当我尝试使用给定的x和y值时,此功能效果很好。

def f(x, y):
    total = 0
    u = np.zeros(10)
    for i in range(0,10):
        u[i] = x * i + y* i
        if u[i] < 10:
            print('do something')
    total = total + u[i]        
    return total

我想使用matplotlib创建3d等高线图。尝试过

f(3,4)
Out[49]: 63.0

我必须为3d图创建一个网格。尝试此操作时,由于函数中的循环,出现错误。我收到错误消息


x = np.linspace(-6, 6, 30)
y = np.linspace(-6, 6, 30)

X, Y = np.meshgrid(x, y)
Z = f(X, Y)

fig = plt.figure()
ax = plt.axes(projection='3d')
ax.contour3D(X, Y, Z, 50, cmap='binary')
ax.set_xlabel('x')
ax.set_ylabel('y')
ax.set_zlabel('z');

如果我的函数有循环,如何绘制3d图形?

1 个答案:

答案 0 :(得分:2)

您需要np.vectorize

# same setup as above, then
Z = np.vectorize(f)(X, Y)

import pylab as plt
plt.imshow(Z, extent=[x[0], x[-1], y[0], y[-1]])

(我与imshow进行了核对,但contour3D也可以使用。)

np.vectorize将采用一个接受标量(非数组)参数并神奇地遍历数组的函数。名义上等同于:

Z2 = np.array([f(xx, yy) for xx in x for yy in y]).reshape(X.shape)
print(np.abs(Z - Z2).max()) # should print 0

但是更快:我在print中删除了f之后:

In [47]: %timeit Z = np.vectorize(f)(X, Y)
6 ms ± 339 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

In [48]: %timeit Z2 = np.array([f(xx, yy) for xx in x for yy in y]).reshape(X.shape)
13.7 ms ± 310 µs per loop (mean ± std. dev. of 7 runs, 100 loops each)

(由于打印速度很慢,我不得不删除打印件以便进行计时。)