在图表的原点开始 Y 刻度,在 matplotlib pyplot 中轴结束的地方结束刻度
Start the Y ticks at origin of graph and end tick where the axis ends in matplotlib pyplot
我希望轴刻度在轴开始和结束的地方开始和结束
我有多个列需要一次绘制。在 for 循环中,我无法为每一列定义 y 刻度,因为它们具有不同的值范围。我想要一个代码来为每一列的图做如图所示的轴设置
这是我正在使用的代码片段
import random
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import openpyxl
import os
from PIL import Image
import io
x = np.random.randint( 10, 100, size = (50, 4) )
y = np.random.randint( 1, 20, size = (50, 4) )
z = np.concatenate((x,y), axis = 1)
df = pd.DataFrame( z, columns=list('ABCDEFGH') )
columns=list('ABCDEFGH')
cat = ['Cat1','Cat2','Cat3']
cat_list = random.choices(cat,k = 50)
df["Cat"] = cat_list
barWidth = 0.25
# loop over multiple colums to plot as bar graph
for i in columns[0:6]:
print(i)
# The bars classidied according to
bars0 = [ df[df['Cat'] == 'Cat1' ][i].mean(),
df[df['Cat'] == 'Cat1' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean() ]
# bars 0 represents all the Cat 1 participants
yerr0 = [
df[df['Cat'] == 'Cat1' ][i].std(),
df[df['Cat'] == 'Cat1' ][i].std(),
df[ df['Cat'] == 'Cat1' ][i].std(),
df[ df['Cat'] == 'Cat1' ][i].std(),
df[ df['Cat'] == 'Cat1' ][i].std(),
df[ df['Cat'] == 'Cat1' ][i].std() ]
bars1 = [ df[df['Cat'] == 'Cat2' ][i].mean(),
df[df['Cat'] == 'Cat2' ][i].mean(),
df[ df['Cat'] == 'Cat2' ][i].mean(),
df[ df['Cat'] == 'Cat2' ][i].mean(),
df[ df['Cat'] == 'Cat2' ][i].mean(),
df[ df['Cat'] == 'Cat2' ][i].mean() ]
# bars 1 represents all the Cat 2 participants
yerr1 = [
df[df['Cat'] == 'Cat2' ][i].std(),
df[df['Cat'] == 'Cat2' ][i].std(),
df[ df['Cat'] == 'Cat2' ][i].std(),
df[ df['Cat'] == 'Cat2' ][i].std(),
df[ df['Cat'] == 'Cat2' ][i].std(),
df[ df['Cat'] == 'Cat2' ][i].std() ]
bars8 = [ df[df['Cat'] == 'Cat3' ][i].mean(),
df[df['Cat'] == 'Cat3' ][i].mean(),
df[ df['Cat'] == 'Cat3' ][i].mean(),
df[ df['Cat'] == 'Cat3' ][i].mean(),
df[ df['Cat'] == 'Cat3' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean()]
# bars 8 represents all the Cat 3 participants
yerr8 = [
df[df['Cat'] == 'Cat3' ][i].std(),
df[df['Cat'] == 'Cat3' ][i].std(),
df[ df['Cat'] == 'Cat3' ][i].std(),
df[ df['Cat'] == 'Cat3' ][i].std(),
df[ df['Cat'] == 'Cat3' ][i].std(),
df[ df['Cat'] == 'Cat3' ][i].std() ]
# standard deciation for the y error bar
r1 = np.arange(len(bars1))
r2 = [x + barWidth for x in r1]
r3 = [x + barWidth for x in r2]
fig, ax = plt.subplots()
right_side = ax.spines["right"]
right_side.set_visible(False)
top_side = ax.spines["top"]
top_side.set_visible(False)
# Cat1
plt.bar(r1 ,bars0,color='r', width=barWidth, edgecolor='white',
label='Cat1',yerr=yerr0)
# Cat2
plt.bar(r2,bars1,color='g', width=barWidth, edgecolor='white',
label='Cat2', yerr=yerr1)
# Cat3
plt.bar(r3,bars8, color='b', width=barWidth,
edgecolor='white', label='Cat3', yerr=yerr8)
plt.xlabel('columns', fontdict={'fontname': 'Arial', 'fontsize': 16,'fontweight':'bold'})
plt.ylabel('AVG '+ columns[columns.index(i)] ,fontdict={'fontname': 'Arial', 'fontsize': 16})
plt.title(columns[columns.index(i)] ,fontdict={'fontname': 'Arial', 'fontsize': 24})
plt.xticks([r + barWidth for r in range(len(bars1))],
[ 'A', 'B',
'C', 'D', 'E', 'F'],fontsize=12)
当我单独定义 plt.yticks() 时,我能够实现右侧的图形。我无法弄清楚如何在循环中做到这一点
只需在循环末尾添加 plt.ylim(top=plt.yticks()[0][-1])
。这利用了一个事实,即自动生成的 yticks 也包含下一个更高的报价,即使它不可见。例如,
print(plt.ylim())
print(plt.yticks()[0])
在你的循环中给出
(0.0, 16.5362767162174)
[ 0. 2. 4. 6. 8. 10. 12. 14. 16. 18.]
所以即使 y 轴变为 16.53...,最大 ytick(不可见,轴外)已经存在。所以我们所要做的就是将 ylim 的顶部设置为这个最大值,使 y 轴稍微延长一点。
当然,这会导致轴略微延长,因此图中的数据可能有点长。但基于这个例子,它看起来没问题。它也对应于您在问题中显示的内容。此外,为了使这个更优化,需要在重新创建自动 yticks 方面付出更多的努力,这可能不值得。
我希望轴刻度在轴开始和结束的地方开始和结束
这是我正在使用的代码片段
import random
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
import openpyxl
import os
from PIL import Image
import io
x = np.random.randint( 10, 100, size = (50, 4) )
y = np.random.randint( 1, 20, size = (50, 4) )
z = np.concatenate((x,y), axis = 1)
df = pd.DataFrame( z, columns=list('ABCDEFGH') )
columns=list('ABCDEFGH')
cat = ['Cat1','Cat2','Cat3']
cat_list = random.choices(cat,k = 50)
df["Cat"] = cat_list
barWidth = 0.25
# loop over multiple colums to plot as bar graph
for i in columns[0:6]:
print(i)
# The bars classidied according to
bars0 = [ df[df['Cat'] == 'Cat1' ][i].mean(),
df[df['Cat'] == 'Cat1' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean() ]
# bars 0 represents all the Cat 1 participants
yerr0 = [
df[df['Cat'] == 'Cat1' ][i].std(),
df[df['Cat'] == 'Cat1' ][i].std(),
df[ df['Cat'] == 'Cat1' ][i].std(),
df[ df['Cat'] == 'Cat1' ][i].std(),
df[ df['Cat'] == 'Cat1' ][i].std(),
df[ df['Cat'] == 'Cat1' ][i].std() ]
bars1 = [ df[df['Cat'] == 'Cat2' ][i].mean(),
df[df['Cat'] == 'Cat2' ][i].mean(),
df[ df['Cat'] == 'Cat2' ][i].mean(),
df[ df['Cat'] == 'Cat2' ][i].mean(),
df[ df['Cat'] == 'Cat2' ][i].mean(),
df[ df['Cat'] == 'Cat2' ][i].mean() ]
# bars 1 represents all the Cat 2 participants
yerr1 = [
df[df['Cat'] == 'Cat2' ][i].std(),
df[df['Cat'] == 'Cat2' ][i].std(),
df[ df['Cat'] == 'Cat2' ][i].std(),
df[ df['Cat'] == 'Cat2' ][i].std(),
df[ df['Cat'] == 'Cat2' ][i].std(),
df[ df['Cat'] == 'Cat2' ][i].std() ]
bars8 = [ df[df['Cat'] == 'Cat3' ][i].mean(),
df[df['Cat'] == 'Cat3' ][i].mean(),
df[ df['Cat'] == 'Cat3' ][i].mean(),
df[ df['Cat'] == 'Cat3' ][i].mean(),
df[ df['Cat'] == 'Cat3' ][i].mean(),
df[ df['Cat'] == 'Cat1' ][i].mean()]
# bars 8 represents all the Cat 3 participants
yerr8 = [
df[df['Cat'] == 'Cat3' ][i].std(),
df[df['Cat'] == 'Cat3' ][i].std(),
df[ df['Cat'] == 'Cat3' ][i].std(),
df[ df['Cat'] == 'Cat3' ][i].std(),
df[ df['Cat'] == 'Cat3' ][i].std(),
df[ df['Cat'] == 'Cat3' ][i].std() ]
# standard deciation for the y error bar
r1 = np.arange(len(bars1))
r2 = [x + barWidth for x in r1]
r3 = [x + barWidth for x in r2]
fig, ax = plt.subplots()
right_side = ax.spines["right"]
right_side.set_visible(False)
top_side = ax.spines["top"]
top_side.set_visible(False)
# Cat1
plt.bar(r1 ,bars0,color='r', width=barWidth, edgecolor='white',
label='Cat1',yerr=yerr0)
# Cat2
plt.bar(r2,bars1,color='g', width=barWidth, edgecolor='white',
label='Cat2', yerr=yerr1)
# Cat3
plt.bar(r3,bars8, color='b', width=barWidth,
edgecolor='white', label='Cat3', yerr=yerr8)
plt.xlabel('columns', fontdict={'fontname': 'Arial', 'fontsize': 16,'fontweight':'bold'})
plt.ylabel('AVG '+ columns[columns.index(i)] ,fontdict={'fontname': 'Arial', 'fontsize': 16})
plt.title(columns[columns.index(i)] ,fontdict={'fontname': 'Arial', 'fontsize': 24})
plt.xticks([r + barWidth for r in range(len(bars1))],
[ 'A', 'B',
'C', 'D', 'E', 'F'],fontsize=12)
当我单独定义 plt.yticks() 时,我能够实现右侧的图形。我无法弄清楚如何在循环中做到这一点
只需在循环末尾添加 plt.ylim(top=plt.yticks()[0][-1])
。这利用了一个事实,即自动生成的 yticks 也包含下一个更高的报价,即使它不可见。例如,
print(plt.ylim())
print(plt.yticks()[0])
在你的循环中给出
(0.0, 16.5362767162174)
[ 0. 2. 4. 6. 8. 10. 12. 14. 16. 18.]
所以即使 y 轴变为 16.53...,最大 ytick(不可见,轴外)已经存在。所以我们所要做的就是将 ylim 的顶部设置为这个最大值,使 y 轴稍微延长一点。
当然,这会导致轴略微延长,因此图中的数据可能有点长。但基于这个例子,它看起来没问题。它也对应于您在问题中显示的内容。此外,为了使这个更优化,需要在重新创建自动 yticks 方面付出更多的努力,这可能不值得。