简体   繁体   English

我如何 plot 条形图宽度可变但在 Python 中没有间隙,并在 x 轴上添加条形宽度作为标签?

[英]How can I plot bar plots with variable widths but without gaps in Python, and add bar width as labels on the x-axis?

I have three lists: x, y and w as shown: x is the name of objects.我有三个列表:x、y 和 w,如图所示:x 是对象的名称。 y is its height and w is its width. y 是它的高度,w 是它的宽度。

x = ["A","B","C","D","E","F","G","H"]

y = [-25, -10, 5, 10, 30, 40, 50, 60]

w = [30, 20, 25, 40, 20, 40, 40, 30]

I'd like to plot these values in a bar plot in Python such that y represents height and w represents width of the bar.我想 plot 这些值在 Python 中的条形 plot 中,这样 y 代表高度,w 代表条形的宽度。

When I plot it using当我使用 plot 它时

colors = ["yellow","limegreen","green","blue","red","brown","grey","black"]

plt.bar(x, height = y, width = w, color = colors, alpha = 0.8)

I get a plot as shown:我得到一个 plot ,如图所示: 在此处输入图像描述

Next, I tried to normalize the widths so that the bars would not overlap with each other using接下来,我尝试标准化宽度,以便条形不会相互重叠使用

w_new = [i/max(w) for i in w]
plt.bar(x, height = y, width = w_new, color = colors, alpha = 0.8)
#plt.axvline(x = ?)
plt.xlim((-0.5, 7.5))

I get much better results than before as shown:我得到了比以前更好的结果,如图所示: 在此处输入图像描述

However, the gaps between the bars are still uneven.但是,钢筋之间的间隙仍然不均匀。 For example, between B and C, there is large gap.比如B和C之间,就有很大的差距。 But between F and G, there is no gap.但在F和G之间,没有差距。

I'd like to have plots where there is even gap width or no gap between two consecutive bars.我想绘制两个连续条之间的间隙宽度均匀或没有间隙的图。 It should look something as shown:它应该如下所示: 在此处输入图像描述

How can I create this type of plot in Python?如何在 Python 中创建这种类型的 plot? Is it possible using any data visualization libraries such as matplotlib, seaborn or Plotly?是否可以使用任何数据可视化库,例如 matplotlib、seaborn 或 Plotly? Is there any alternative to do it if the data is available in dataframe?如果数据在 dataframe 中可用,是否有任何替代方法?

Additionally, I'd like to add labels for A, B, C, etc. to the right of the plot and rather have actual width of the bar as labels on the x-axis (for eg depicted by red numbers in the x-axis plot above).此外,我想在 plot 的右侧添加 A、B、C 等标签,而是将条形的实际宽度作为 x 轴上的标签(例如用 x-轴 plot 以上)。 I'd also like to add a vertical red line at distance 50 from the x-axis.我还想在距离 x 轴 50 处添加一条垂直红线。 I know this can be added using plt.axvline(x =...) But I am not sure what is the value I should state as x as the scale of W is not exact with the length of x-axis.我知道这可以使用plt.axvline(x =...)添加,但我不确定 state 作为 x 的值是多少,因为 W 的比例与 x 轴的长度不完全一致。

IIUC, you can try something like this: IIUC,你可以尝试这样的事情:

import matplotlib.pyplot as plt

x = ["A","B","C","D","E","F","G","H"]

y = [-25, -10, 5, 10, 30, 40, 50, 60]

w = [30, 20, 25, 40, 20, 40, 40, 30]

colors = ["yellow","limegreen","green","blue","red","brown","grey","black"]

#plt.bar(x, height = y, width = w, color = colors, alpha = 0.8)

xticks=[]
for n, c in enumerate(w):
    xticks.append(sum(w[:n]) + w[n]/2)
    
w_new = [i/max(w) for i in w]
a = plt.bar(xticks, height = y, width = w, color = colors, alpha = 0.8)
_ = plt.xticks(xticks, x)

plt.legend(a.patches, x)

Output: Output:

在此处输入图像描述

Or change xticklabels for bar widths:或更改条形宽度的 xticklabels:

xticks=[]
for n, c in enumerate(w):
    xticks.append(sum(w[:n]) + w[n]/2)
    
w_new = [i/max(w) for i in w]
a = plt.bar(xticks, height = y, width = w, color = colors, alpha = 0.8)
_ = plt.xticks(xticks, w)
plt.legend(a.patches, x)

Output: Output:

在此处输入图像描述

I figured out an alternative way to do this.我想出了另一种方法来做到这一点。

x = ["A","B","C","D","E","F","G","H"]

y = [-25, -10, 5, 10, 30, 40, 50, 60]

w = [30, 20, 25, 40, 20, 40, 40, 30]

xpos = []

a = 0
for i in range(len(w)):
    if i == 0:
        a+=w[i]
       
        xpos.append(w[i]/2)
        
    else:
        a += w[i]
       
        xpos.append(a - w[i]/2)

colors = ["yellow","limegreen","green","blue","red","brown","grey","black"]


fig = plt.bar(xpos,
        height = y,
        width = w,
        color = colors,
        alpha = 0.5,
      )

plt.xticks(ticks = xpos, labels = w)

plt.xlim((0, 245))
plt.axvline(x = 150)
plt.legend(fig.patches, x)

plt.show()

在此处输入图像描述

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM