Matplotlib Polar Plot with Lines

时间:2016-04-23 20:48:56

标签: python matplotlib python-2.6

尝试使用线条代替条形在Matplotlib中创建风玫瑰。换句话说,我想要这样的东西(用Gnuplot创建),其中线条沿着整个长度具有一致的厚度,并且沿着径向从原点延伸到风速(红色是最新的观察,靛蓝是巅峰时期,随着年龄的增长,年长的痘痘会变暗:

wind rose 1

我最接近的就是这个(请忽略除线条之外的任何差异):

wind rose 2

我尝试过的所有内容都以“粉丝们”的方式绘制。从原点 - 无论是酒吧,线条,箭头等等。这是情节线:

bars = ax.bar(wind_direction, wind_speed, width=.075, linewidth=0.1, edgecolor='black', zorder=3)

SOLUTION:

Solution

这是完整的代码,用于创建所需的绘图(在此行的正上方),感谢@ cphlewis'固定。尝试使用plot时我的错误是在一个命令中绘制所有数据,而不是' n'图的数量(单独绘制每一行。)

#! /usr/bin/env python2.6
# -*- coding: utf-8 -*-

import csv
import numpy as np
import matplotlib.pyplot as plt

bar_colors     = ['#333333', '#444444', '#555555', '#666666', '#777777', '#888888', '#999999', 'red']
data_source    = '/Users/username/Dropbox/Public/charts.csv'
num_obs        = 8
final_data     = []
wind_direction = []
wind_speed     = []

# Get the data.
data_file = open(data_source, "r")
csv_data  = csv.reader(data_file, delimiter=',')
[final_data.append(item) for item in csv_data]
data_file.close()

# Grab the column headings for the labels, then delete the row from final_data.
xlabel = final_data[0][24]
ylabel = final_data[0][25]
final_data.pop(0)

# Create lists of data to plot (string -> float).
[wind_direction.append(float(item[24])) for item in final_data]
[wind_speed.append(float(item[25])) for item in final_data]

# Make them the desired length based on num_obs.
wind_direction = wind_direction[len(wind_direction)-num_obs:len(wind_direction)]
wind_speed     = wind_speed[len(wind_speed)-num_obs:len(wind_speed)]

# Polar plots are in radians (not degrees.)
wind_direction = np.radians(wind_direction)


wind = zip(wind_direction, wind_speed, bar_colors) # polar(theta,r)


# Customizations.
plt.figure(figsize=(3, 3))  # Size
ax = plt.subplot(111, polar=True)  # Create subplot
plt.grid(color='#888888')  # Color the grid
ax.set_theta_zero_location('N')  # Set zero to North
ax.set_theta_direction(-1)  # Reverse the rotation
ax.set_xticklabels(['N', 'NE', 'E', 'SE', 'S', 'SW', 'W', 'NW'], color='#666666', fontsize=8)  # Customize the xtick labels
ax.spines['polar'].set_visible(False)  # Show or hide the plot spine
ax.set_axis_bgcolor('#111111')  # Color the background of the plot area.

# Create the plot.
# Note: zorder of the plot must be >2.01 for the plot to be above the grid (the grid defaults to z=2.)
for w in wind:
    ax.plot((0, w[0]), (0, w[1]), color=w[2], linewidth=2, zorder=3)

# Right-size the grid (must be done after the plot), and customize the tick labels.
if max(wind_speed) <= 5:
    ax.yaxis.set_ticks(np.arange(1, 5, 1))
    ax.set_rgrids([1, 2, 3, 4, 5], angle=67, color='#FFFFFF', horizontalalignment='left', verticalalignment='center', fontsize=8)
elif 5 < max(wind_speed) <= 10:
    ax.yaxis.set_ticks(np.arange(2, 10, 2))
    ax.set_rgrids([2, 4, 6, 8, 10], angle=67, color='#FFFFFF', horizontalalignment='left', verticalalignment='center', fontsize=8)
elif 10 < max(wind_speed) <= 20:
    ax.yaxis.set_ticks(np.arange(5, 20, 5))
    ax.set_rgrids([5, 10, 15, 20], angle=67, color='#FFFFFF', horizontalalignment='left', verticalalignment='center', fontsize=8)
elif 20 < max(wind_speed) <= 50:
    ax.yaxis.set_ticks(np.arange(10, 50, 10))
    ax.set_rgrids([10, 20, 30, 40, 50], angle=67, color='#FFFFFF', horizontalalignment='left', verticalalignment='center', fontsize=8)
elif 50 < max(wind_speed):
    plt.text(0.5, 0.5, u'Holy crap!', color='white', horizontalalignment='center', verticalalignment='center', transform=ax.transAxes, bbox=dict(facecolor='red', alpha=0.5))

# Plot circles for current obs and max wind.
fig = plt.gcf()
max_wind_circle = plt.Circle((0, 0), max(wind_speed), transform=ax.transData._b, fill=False, edgecolor='indigo', linewidth=2, alpha=1, zorder=9)
fig.gca().add_artist(max_wind_circle)
last_wind_circle = plt.Circle((0, 0), wind_speed[num_obs-1], transform=ax.transData._b, fill=False, edgecolor='red', linewidth=2, alpha=1, zorder=10)
fig.gca().add_artist(last_wind_circle)

# If latest obs is a speed of zero, plot something that we can see.
if wind_speed[num_obs-1] == 0:
    zero_wind_circle = plt.Circle((0, 0), 0.1, transform=ax.transData._b, fill=False, edgecolor='red', alpha=1)
    fig.gca().add_artist(zero_wind_circle)

# Save it to a file.
plt.savefig('/Users/username/Desktop/wind.png', facecolor='black', edgecolor='none')

1 个答案:

答案 0 :(得分:3)

你真正的问题是,如何用线而不是条形图绘制极坐标图?答案:plot。这样做的最小和完整的例子:

#! /usr/bin/env python2.6
# -*- coding: utf-8 -*-

import csv
import numpy as np
import matplotlib.pyplot as plt

bar_colors     = ['#333333', '#444444', '#555555', '#666666', '#777777', '#888888', '#999999', '#AA0000']
num_obs        = len(bar_colors)

# Make up some data
wind_direction = (2*3.14)*(np.random.random_sample(num_obs))
wind_speed = 5 * np.random.random_sample(num_obs)
wind = zip(wind_direction, wind_speed, bar_colors) # polar(theta,r)

# Polar plotting
fig = plt.figure(figsize=(3, 3))  # Size
ax = plt.subplot(111, polar=True)  # Create subplot
plt.grid(color='#888888')  # Color the grid
ax.set_theta_zero_location('N')  # Set zero to North

for w in wind:
    #ax.plot(wind_speed, wind_direction, c = bar_colors, zorder = 3)
    ax.plot((0, w[0]), ( 0, w[1]), c = w[2], zorder = 3)

fig.show()

enter image description here