我知道这个线程已经死了很长时间了,但我认为发布我的解决方案可能对任何试图弄清楚如何有效地在对数刻度图上绘制箭头的人有所帮助。
作为其他人已经发布的替代方案,您可以使用转换对象来输入箭头坐标,而不是原始轴的比例,而是“轴坐标”的(线性)比例。我所说的轴坐标是通过 [0,1](垂直范围)归一化为 [0,1](水平范围)的坐标,其中点 (0,0) 是左下角,点(1,1) 将是右上角,依此类推。然后你可以简单地包括一个箭头:
plt.arrow(0.1, 0.1, 0.9, 0.9, transform=plot1.transAxes, length_includes_head=True)
这给出了一个对角线跨越绘图水平和垂直范围的 4/5 的箭头,从左下角到右上角(plot1
子图名称在哪里)。
如果您想在一般情况下执行此操作,可以为箭头指定精确坐标(x0,y0)
和对数空间,如果您编写两个函数并将原始坐标转换为这些“轴”坐标(x1,y1)
,这并不难。我已经给出了一个示例,说明如何可以修改 OP 发布的原始代码以在下面实现这一点(抱歉不包括代码生成的图像,我还没有所需的声誉)。fx(x)
fy(y)
#!/usr/bin/python3
import numpy as np
import matplotlib.pyplot as plt
import matplotlib as mpl
# functions fx and fy take log-scale coordinates to 'axes' coordinates
ax = 1E-12 # [ax,bx] is range of horizontal axis
bx = 1E0
def fx(x):
return (np.log(x) - np.log(ax))/(np.log(bx) - np.log(ax))
ay = 1E-20 # [ay,by] is range of vertical axis
by = 1E-10
def fy(y):
return (np.log(y) - np.log(ay))/(np.log(by) - np.log(ay))
plot1 = plt.subplot(111)
plt.xscale('log')
plt.yscale('log')
plt.xlim(ax, bx)
plt.ylim(ay, by)
# transformed coordinates for arrow from (1E-10,1E-18) to (1E-4,1E-16)
x0 = fx(1E-10)
y0 = fy(1E-18)
x1 = fx(1E-4) - fx(1E-10)
y1 = fy(1E-16) - fy(1E-18)
plt.arrow(
x0, y0, x1, y1, # input transformed arrow coordinates
transform = plot1.transAxes, # tell matplotlib to use axes coordinates
facecolor = 'black',
length_includes_head=True
)
plt.grid(True)
plt.savefig('test.pdf')