根据if条件(matplot animate python)对标记进行数字化更改

3zwjbxry  于 2023-06-25  发布在  Python
关注(0)|答案(2)|浏览(144)

我有一个点的列表,我转换成数组后,我想显示点与标记'o',如果点和移动的点之间的距离超过10,例如,点的标记从'o'到'*',我只是尝试这样做,但所有的标记改变不仅从节点谁是条件下的标记.有人能帮我吗
下面是一个没有移动的点的代码示例,我只是设置了一个静态条件,这是我的第一步,我想改变标记但不是所有的点,只对那些处于if条件下的点:

  1. import matplotlib.pyplot as plt
  2. from matplotlib.animation import FuncAnimation
  3. def createList(r1, r2):
  4. return [item for item in range(r1, r2+1)]
  5. r1, r2 = 1, 50
  6. mialistax=createList(r1, r2)
  7. mialistay=createList(r1, r2)
  8. fig, ax = plt.subplots()
  9. import numpy as np
  10. x_l=np.array(mialistax)
  11. y_l = np.array(mialistay)
  12. def animate(i):
  13. max_x= max(mialistax)
  14. max_y=max(mialistay)
  15. ax.clear()
  16. if (x_l[i]>10):
  17. mark='*'
  18. else:
  19. mark='o'
  20. ax.plot(x_l[i],y_l[i],marker=mark)
  21. ax.set_xlim([0,max_x])
  22. ax.set_ylim([0,max_y])
  23. plt.plot(x_l,y_l,marker=mark)
  24. ani = FuncAnimation(fig, animate, frames=200, interval=500, repeat=False)
  25. plt.show()

在这段代码中,所有点的标记都发生了变化,我希望标记只为那些在if条件下的点发生变化。

zfciruhq

zfciruhq1#

当你将frame设置为整数时,例如你所做的frames=200,那么range(200)将被传递给animate()函数,并且animate(i)的参数被视为函数定义中的整数,而不是range对象。相反,你可以设置一个迭代对象,比如python list或numpy array作为frame参数。请运行下面的代码来获得框架参数的想法:

  1. import matplotlib.pyplot as plt
  2. from matplotlib.animation import FuncAnimation
  3. def createList(r1, r2):
  4. return [item for item in range(r1, r2+1)]
  5. r1, r2 = 1, 50
  6. mialistax=createList(r1, r2)
  7. mialistay=createList(r1, r2)
  8. fig, ax = plt.subplots()
  9. import numpy as np
  10. x_l=np.array(mialistax)
  11. y_l = np.array(mialistay)
  12. def animate(i):
  13. max_x= max(mialistax)
  14. max_y=max(mialistay)
  15. ax.clear()
  16. if (x_l[i]>10):
  17. mark='*'
  18. else:
  19. mark='o'
  20. ax.plot(x_l[i],y_l[i],marker=mark)
  21. ax.set_xlim([0,max_x])
  22. ax.set_ylim([0,max_y])
  23. plt.plot(x_l,y_l,marker=mark)
  24. ani = FuncAnimation(fig, animate, frames=[5,15], interval=500, repeat=True)
  25. plt.show()
展开查看全部
xuo3flqw

xuo3flqw2#

如果我对这个问题的理解是正确的,您需要一个显示所有点的动画,但是如果索引i(帧编号)处的点的x值大于10,则应将其转换为"*"标记。
首先,你有三个问题。第一个是你阴谋的顺序。

  1. ax.plot(x_l[i], y_l[i], marker=mark)
  2. ax.plot(x_l, y_l, marker=mark)

这意味着您首先绘制单个点,然后在顶部绘制其余点。所以你不会看到你的“特殊”点,因为它被其他点掩盖了。
第二个问题是您为两个图设置了相同的标记(单个点和其余点)。我将创建一个所有标记的列表,如果满足条件,则更新索引i处的标记。然后,循环遍历所有点并分别绘制它们(因为无法传递标记列表)。您可能希望您的“特殊”点突出,这样我们就可以将其显示为不同的颜色。

  1. markers = ["o"]*len(x_l)
  2. def animate(i):
  3. max_x = max(x_l)
  4. max_y = max(y_l)
  5. ax.clear()
  6. if x_l[i] > 10:
  7. markers[i] = '*'
  8. ax.set_xlim([0, max_x])
  9. ax.set_ylim([0, max_y])
  10. for indx, (x, y, marker) in enumerate(zip(x_l, y_l, markers)):
  11. color = "tab:orange" if indx == i else "tab:blue"
  12. ax.plot(x, y, marker=marker, color=color)

最后,你只有50个点,但是有frames=200,所以你需要增加你的点或减少帧的数量来匹配。

  1. ani = FuncAnimation(fig, animate, frames=len(x_l), interval=5, repeat=False)

我假设你是Python新手,所以我还将提出其他建议来改进你的代码。
1.您可以使用list函数直接从range创建列表:list(range(start, stop))。因为你要将它转换为numpy数组,所以有一个numpy函数:np.arange(start, stop)
1.对于numpy数组,你可以使用max方法:x_l.max(),虽然这个变化并不重要。

  1. import matplotlib.pyplot as plt
  2. import numpy as np
  3. from matplotlib.animation import FuncAnimation
  4. plt.close("all")
  5. r1 = 1
  6. r2 = 50
  7. x_l = np.arange(r1, r2+1)
  8. y_l = np.arange(r1, r2+1)
  9. fig, ax = plt.subplots()
  10. markers = ["o"]*x_l.shape[0]
  11. def animate(i):
  12. max_x = x_l.max()
  13. max_y = y_l.max()
  14. ax.cla()
  15. if x_l[i] > 10:
  16. markers[i] = '*'
  17. for indx, (x, y, marker) in enumerate(zip(x_l, y_l, markers)):
  18. color = "tab:orange" if indx == i else "tab:blue"
  19. ax.plot(x, y, marker=marker, color=color)
  20. ax.set_xlim([0, max_x])
  21. ax.set_ylim([0, max_y])
  22. ani = FuncAnimation(fig, animate, frames=x_l.shape[0], interval=500, repeat=False)
  23. fig.show()
展开查看全部

相关问题