Matplotlib:使用包含子图的自定义绘图功能在同一图形中循环绘图

dojqjjoe  于 2022-11-15  发布在  其他
关注(0)|答案(1)|浏览(144)

我有一个具有多个ID的数据框,希望为每个ID创建一个断轴图。我还希望在同一图中绘制所有内容,而不是为每个ID创建单独的图。我的玩具示例生成单独的图,但我更希望两个图重叠,如下面的小图所示

  1. df = pd.DataFrame({'id':['id1','id1','id1','id1','id1','id1','id1','id1','id1','id1',
  2. 'id2','id2','id2','id2','id2','id2','id2','id2','id2','id2'],
  3. 'x': [0, 1, 2, 3, 4, 5, 1000, 2000, 3000, 4000,
  4. 0, 1, 2, 3, 4, 5, 1000, 2000, 3000, 4000,],
  5. 'y': [5, 4, 5, 4, 7, 6, 5, 4, 3, 2,
  6. 1, 2, 3, 4, 7, 7, 8, 7, 9, 5]})
  7. def _custom_plot(frame):
  8. x = frame['x']
  9. y = frame['y']
  10. f,(ax,ax2) = plt.subplots(1,2,sharey=True, facecolor='w', figsize=(15, 5))
  11. # plot the same data on both axes
  12. ax.plot(x, y, 'o--', color='grey', alpha=0.3)
  13. ax2.plot(x, y, 'o--', color='grey', alpha=0.3)
  14. ax.set_xlim(0,100)
  15. ax2.set_xlim(1e3,5e3)
  16. # hide the spines between ax and ax2
  17. ax.spines['right'].set_visible(False)
  18. ax2.spines['left'].set_visible(False)
  19. ax.yaxis.tick_left()
  20. #ax.tick_params(labelright='off')
  21. ax2.yaxis.tick_right()
  22. d = .015 # how big to make the diagonal lines in axes coordinates
  23. # arguments to pass plot, just so we don't keep repeating them
  24. kwargs = dict(transform=ax.transAxes, color='k', clip_on=False)
  25. ax.plot((1-d,1+d), (-d,+d), **kwargs)
  26. ax.plot((1-d,1+d),(1-d,1+d), **kwargs)
  27. kwargs.update(transform=ax2.transAxes) # switch to the bottom axes
  28. ax2.plot((-d,+d), (1-d,1+d), **kwargs)
  29. ax2.plot((-d,+d), (-d,+d), **kwargs)
  30. plt.yticks([0, 1, 2, 3, 4], [0, 1, 2, 3, 4])
  31. plt.show()
  32. for id in df['id'].unique():
  33. _custom_plot(df[df['id']==id])

kkbh8khc

kkbh8khc1#

我不确定你的评论@cphlewis是否朝着这个方向去了,但我想通了这样的工作方式

  1. df = pd.DataFrame({'id':['id1','id1','id1','id1','id1','id1','id1','id1','id1','id1', 'id2','id2','id2','id2','id2','id2','id2','id2','id2','id2'],
  2. 'x': [0, 1, 2, 3, 4, 5, 1000, 2000, 3000, 4000, 0, 1, 2, 3, 4, 5, 1000, 2000, 3000, 4000,],
  3. 'y': [5, 4, 5, 4, 7, 6, 5, 4, 3, 2, 1, 2, 3, 4, 7, 7, 8, 7, 9, 5]})
  4. def _sub_plot(frame, ax=None):
  5. x = frame['x']
  6. y = frame['y']
  7. if ax is None:
  8. ax = plt.gca()
  9. # plot the same data on both axes
  10. line = ax.plot(x, y, 'o--', color='grey', alpha=0.3)
  11. return line
  12. def _main_plot(df, listofkeys, key):
  13. f,(ax1,ax2) = plt.subplots(1,2,sharey=True, facecolor='w', figsize=(15, 5))
  14. for l in listofkeys:
  15. frame = df[df[key] == l]
  16. _sub_plot(frame, ax1)
  17. _sub_plot(frame, ax2)
  18. ax1.set_xlim(0,100)
  19. ax2.set_xlim(1e3,5e3)
  20. # hide the spines between ax and ax2
  21. ax1.spines['right'].set_visible(False)
  22. ax2.spines['left'].set_visible(False)
  23. ax1.yaxis.tick_left()
  24. #ax.tick_params(labelright='off')
  25. ax2.yaxis.tick_right()
  26. d = .015 # how big to make the diagonal lines in axes coordinates
  27. # arguments to pass plot, just so we don't keep repeating them
  28. kwargs = dict(transform=ax1.transAxes, color='k', clip_on=False)
  29. ax1.plot((1-d,1+d), (-d,+d), **kwargs)
  30. ax1.plot((1-d,1+d),(1-d,1+d), **kwargs)
  31. kwargs.update(transform=ax2.transAxes) # switch to the bottom axes
  32. ax2.plot((-d,+d), (1-d,1+d), **kwargs)
  33. ax2.plot((-d,+d), (-d,+d), **kwargs)
  34. plt.yticks([0, 1, 2, 3, 4], [0, 1, 2, 3, 4])
  35. _main_plot(df, df['id'].unique(), 'id')

展开查看全部

相关问题