Python Matplotlib polar未按预期打印
我试图插入一个笛卡尔图的极坐标图版本。下面是它的外观(根据在Matlab中完成的类似程序): 这里有足够的代码来显示我所得到的奇怪:Python Matplotlib polar未按预期打印,python,matplotlib,plot,Python,Matplotlib,Plot,我试图插入一个笛卡尔图的极坐标图版本。下面是它的外观(根据在Matlab中完成的类似程序): 这里有足够的代码来显示我所得到的奇怪: from scipy import pi, sin, cos, log from numpy import radians as rad from numpy import log10, linspace from matplotlib import pyplot as plt ############## Inputs ############## #B
from scipy import pi, sin, cos, log
from numpy import radians as rad
from numpy import log10, linspace
from matplotlib import pyplot as plt
############## Inputs ##############
#Beamwidth, in degrees
BW = 5
############## Constants for calculations ##############
# 0 = uniform/sin, 1 = cos, 2 = cos^2, etc
#Peak Pattern break points, from Table 3
p0, p1, p2, p3, p4 = -5.75, -14.4, -22.3, -31.5, -39.4
#Average pattern break points, from Table 3
a0, a1 ,a2, a3, a4 = -12.16, -20.6, -29, -37.6, -42.5
#Constant added to peak pattern to convert it to average, from Table 3
c0, c1, c2, c3, c4 = -3.72, -4.32, -4.6, -4.2, -2.61
#Mask floor levels, from Table 3
floor0, floor1, floor2, floor3, floor4 = -30, -50, -60, -70, -80
############## Calculations ##############
#Lists for plotting purposes
u_x = list(linspace(0,90,500))
u0_norm_y = list()
u0_peak_y = list()
u0_avg_y = list()
##Calculations start
for ang in u_x:
########## Uniform
u0 = pi * 50.8 * sin(rad(ang)) / BW
def u0_norm(ang):
if ang == 0:
return 0
else:
return 20 * log10(abs(sin(u0) / u0))
def u0_peak(ang, u0_norm):
if ang == 0:
return 0
elif u0_norm(ang) > p0:
return u0_norm(ang)
elif -8.584 * log(2.876 * ang / BW) > floor0:
return -8.584 * log(2.876 * ang / BW)
else:
return floor0
def u0_avg(ang, u0_norm):
if ang == 0:
return 0
elif u0_norm(ang) > a0:
return u0_norm(ang)
elif -8.584 * log(2.876 * ang / BW) + c0 > floor0:
return -8.584 * log(2.876 * ang / BW) + c0
else:
return floor0
u0_peak_y.append(u0_peak(ang, u0_norm))
u0_norm_y.append(u0_norm(ang))
u0_avg_y.append(u0_avg(ang, u0_norm))
############## Plots ##############
#Uniform
fig1 = plt.figure()
ax1 = plt.subplot(121)
ax2 = plt.subplot(122, polar = True)
ax1.plot(u_x, u0_norm_y, label= "Normalized Pattern")
ax1.plot(u_x, u0_peak_y, label= "Peak")
ax1.plot(u_x, u0_avg_y, label= "Average")
ax1.set_title("Uniform Pattern")
ax1.set_xlabel("Angle (degrees)")
ax1.set_ylabel("Normalized Antenna Pattern (dB)")
ax2.set_theta_zero_location("N")
ax2.set_theta_direction(-1)
ax2.plot(u_x, u0_norm_y, label= "Normalized Pattern")
ax2.plot(u_x, u0_peak_y, label= "Peak")
ax2.plot(u_x, u0_avg_y, label= "Average")
ax2.set_thetamin(0)
ax2.set_thetamax(90)
ax1.grid(True)
plt.tight_layout()
plt.subplots_adjust(wspace = 0.4)
plt.show()
显然,出了严重的问题。我的阴谋真是一团糟。我假设极坐标图与笛卡尔坐标图的创建方式(代码方面)有很大不同,但我还没有找到任何关于这一点的真正细节。你把弧度和度数混在一起了(重要性的直觉是正确的)。 删除定义u0时对弧度的转换,并直接将输入u_x转换为弧度
from scipy import pi, sin, cos, log
from numpy import radians as rad
from numpy import log10, linspace
from matplotlib import pyplot as plt
############## Inputs ##############
#Beamwidth, in degrees
BW = 5
############## Constants for calculations ##############
# 0 = uniform/sin, 1 = cos, 2 = cos^2, etc
#Peak Pattern break points, from Table 3
p0, p1, p2, p3, p4 = -5.75, -14.4, -22.3, -31.5, -39.4
#Average pattern break points, from Table 3
a0, a1 ,a2, a3, a4 = -12.16, -20.6, -29, -37.6, -42.5
#Constant added to peak pattern to convert it to average, from Table 3
c0, c1, c2, c3, c4 = -3.72, -4.32, -4.6, -4.2, -2.61
#Mask floor levels, from Table 3
floor0, floor1, floor2, floor3, floor4 = -30, -50, -60, -70, -80
############## Calculations ##############
#Lists for plotting purposes
u_x = list(linspace(0,rad(90),500))
u0_norm_y = list()
u0_peak_y = list()
u0_avg_y = list()
##Calculations start
for ang in u_x:
########## Uniform
u0 = pi * 50.8 * sin((ang)) / BW
def u0_norm(ang):
if ang == 0:
return 0
else:
return 20 * log10(abs(sin(u0) / u0))
def u0_peak(ang, u0_norm):
if ang == 0:
return 0
elif u0_norm(ang) > p0:
return u0_norm(ang)
elif -8.584 * log(2.876 * ang / BW) > floor0:
return -8.584 * log(2.876 * ang / BW)
else:
return floor0
def u0_avg(ang, u0_norm):
if ang == 0:
return 0
elif u0_norm(ang) > a0:
return u0_norm(ang)
elif -8.584 * log(2.876 * ang / BW) + c0 > floor0:
return -8.584 * log(2.876 * ang / BW) + c0
else:
return floor0
u0_peak_y.append(u0_peak(ang, u0_norm))
u0_norm_y.append(u0_norm(ang))
u0_avg_y.append(u0_avg(ang, u0_norm))
############## Plots ##############
#Uniform
fig1 = plt.figure()
ax1 = plt.subplot(121)
ax2 = plt.subplot(122, polar = True)
ax1.plot(u_x, u0_norm_y, label= "Normalized Pattern")
ax1.plot(u_x, u0_peak_y, label= "Peak")
ax1.plot(u_x, u0_avg_y, label= "Average")
ax1.set_title("Uniform Pattern")
ax1.set_xlabel("Angle (degrees)")
ax1.set_ylabel("Normalized Antenna Pattern (dB)")
ax2.set_theta_zero_location("N")
ax2.set_theta_direction(-1)
ax2.plot(u_x, u0_norm_y, label= "Normalized Pattern")
ax2.plot(u_x, u0_peak_y, label= "Peak")
ax2.plot(u_x, u0_avg_y, label= "Average")
ax2.set_thetamin(0)
ax2.set_thetamax(90)
ax1.grid(True)
plt.tight_layout()
plt.subplots_adjust(wspace = 0.4)
plt.show()
我认为这是同一代码的更好版本,只需稍加编辑
from scipy import pi, sin, cos, log
from numpy import radians as rad
from numpy import log10, linspace
from matplotlib import pyplot as plt
############## Inputs ##############
#Beamwidth, in degrees
BW = 5
############## Constants for calculations ##############
# 0 = uniform/sin, 1 = cos, 2 = cos^2, etc
#Peak Pattern break points, from Table 3
p0, p1, p2, p3, p4 = -5.75, -14.4, -22.3, -31.5, -39.4
#Average pattern break points, from Table 3
a0, a1 ,a2, a3, a4 = -12.16, -20.6, -29, -37.6, -42.5
#Constant added to peak pattern to convert it to average, from Table 3
c0, c1, c2, c3, c4 = -3.72, -4.32, -4.6, -4.2, -2.61
#Mask floor levels, from Table 3
floor0, floor1, floor2, floor3, floor4 = -30, -50, -60, -70, -80
############## Calculations ##############
#Lists for plotting purposes
u_x = list(linspace(0,rad(90),500))
u0_norm_y = list()
u0_peak_y = list()
u0_avg_y = list()
##Function definition
def u0_norm(ang, u0):
if ang == 0:
return 0
else:
return 20 * log10(abs(sin(u0) / u0))
def u0_peak(ang, u0):
if ang == 0:
return 0
elif u0_norm(ang, u0) > p0:
return u0_norm(ang, u0)
elif -8.584 * log(2.876 * ang / BW) > floor0:
return -8.584 * log(2.876 * ang / BW)
else:
return floor0
def u0_avg(ang, u0):
if ang == 0:
return 0
elif u0_norm(ang, u0) > a0:
return u0_norm(ang, u0)
elif -8.584 * log(2.876 * ang / BW) + c0 > floor0:
return -8.584 * log(2.876 * ang / BW) + c0
else:
return floor0
for ang in u_x:
########## Uniform
u0 = pi * 50.8 * sin(ang) / BW
u0_peak_y.append(u0_peak(ang, u0))
u0_norm_y.append(u0_norm(ang, u0))
u0_avg_y.append(u0_avg(ang, u0))
############## Plots ##############
#Uniform
fig1 = plt.figure()
ax1 = plt.subplot(121)
ax2 = plt.subplot(122, polar = True)
ax1.plot(u_x, u0_norm_y, label= "Normalized Pattern")
ax1.plot(u_x, u0_peak_y, label= "Peak")
ax1.plot(u_x, u0_avg_y, label= "Average")
ax1.set_title("Uniform Pattern")
ax1.set_xlabel("Angle (radians)")
ax1.set_ylabel("Normalized Antenna Pattern (dB)")
ax2.set_theta_zero_location("N")
ax2.set_theta_direction(-1)
ax2.plot(u_x, u0_norm_y, label= "Normalized Pattern")
ax2.plot(u_x, u0_peak_y, label= "Peak")
ax2.plot(u_x, u0_avg_y, label= "Average")
ax2.set_thetamin(0)
ax2.set_thetamax(90)
ax1.grid(True)
plt.tight_layout()
plt.subplots_adjust(wspace = 0.4)
plt.show()
你能用比“古怪”更多的词来描述这个问题吗?可能你只是忘记了将度转换成辐射度?我的代码创建的图实际上是胡说八道。它看起来就像是涂鸦。使用同样的数学方法来创建笛卡尔曲线图效果很好,但将其直接插入到polar中显然不是一种可行的方法。有些输入显然是非常错误的,但我不确定是什么。再说一次,你忘了将度转换为辐射度吗?要进行调试,我首先要简化代码。将函数定义置于for循环之外(可以将u0作为输入参数传递给uo_norm)。此外,它看起来像u0_norm是一个函数,但也是一个变量,这可能不是问题所在,但它肯定会导致读取代码以发现错误的复杂性。据我所知,这不是问题所在。Sin,cos,等等,都需要弧度,所以这些转换都建立在我的方程中。不过,极坐标图似乎确实使用了度数,因为将θ轴设置为显示0-90会给我一个90度的楔形。在trig函数之外,一切都是使用度值来计算的,这似乎是有意义的,至少在数学上是如此。因此,将u_x本身置于弧度中会改变u0_peak和u0_avg的绘制方式(以图形方式,当需要沿着曲线进行跟踪时,它们会向上移动),因此需要进行一些进一步的更改,但是,只要在极坐标图的绘图部分将u_x转换为弧度,就可以解决这个问题,谢谢!我猜数学都是以弧度为单位的,而显示器是以度为单位的。。。另外,我感谢你的编辑!这真的帮助我更好地理解所有这些是如何一起工作的。是的,我可以从数学的角度看,仍然有一些问题需要解决。例如,我突然想到波束宽度BW是以度表示的,所以ang/BW没有意义。另外一个建议:如果您需要将同一常数写入3次,并在计算中使用它…您可能希望将该数字分配给一个具有良好名称的变量(可能是自解释的,至少在您的域中是这样)。我指的是-8.584、2.876。。。这将帮助您避免错误,在需要进行更改时节省时间,并有一种自文档化的代码。