Beri anotasi batang dengan nilai pada plot batang Pandas


95

Saya sedang mencari cara untuk membuat anotasi batang saya di petak batang Pandas dengan nilai numerik bulat dari DataFrame saya.

>>> df=pd.DataFrame({'A':np.random.rand(2),'B':np.random.rand(2)},index=['value1','value2'] )         
>>> df
                 A         B
  value1  0.440922  0.911800
  value2  0.588242  0.797366

Saya ingin mendapatkan sesuatu seperti ini:

contoh anotasi plot batang

Saya mencoba dengan contoh kode ini, tetapi semua penjelasannya berpusat pada tanda x:

>>> ax = df.plot(kind='bar') 
>>> for idx, label in enumerate(list(df.index)): 
        for acc in df.columns:
            value = np.round(df.ix[idx][acc],decimals=2)
            ax.annotate(value,
                        (idx, value),
                         xytext=(0, 15), 
                         textcoords='offset points')

Tom berhasil, tetapi saya punya solusi yang lebih kompleks di sini: stackoverflow.com/questions/19917587/…
Paul H

Jawaban:


155

Anda mendapatkannya langsung dari tambalan sumbu:

for p in ax.patches:
    ax.annotate(str(p.get_height()), (p.get_x() * 1.005, p.get_height() * 1.005))

Anda akan ingin mengubah pemformatan string dan offset untuk memusatkan semuanya, mungkin menggunakan lebarnya dari p.get_width(), tetapi itu seharusnya membantu Anda memulai. Ini mungkin tidak berfungsi dengan plot batang bertumpuk kecuali Anda melacak offset di suatu tempat.


29
Terima kasih @TomAugsPurger, yang berikut ini berhasil: for p in ax.patches: ax.annotate(np.round(p.get_height(),decimals=2), (p.get_x()+p.get_width()/2., p.get_height()), ha='center', va='center', xytext=(0, 10), textcoords='offset points')
leroygr

2
Pertanyaan lain: bagaimana Anda menangani batang dengan nilai negatif? Dengan kode di atas, label selalu dengan koordinat positif, meskipun nilai batangnya negatif.
leroygr

1
Apakah ada solusi serupa untuk batang horizontal: jenis = barh?
Nickpick

4
Saya menemukan ini bekerja untuk barh:ax.annotate(str(p.get_width()), (p.get_x() + p.get_width(), p.get_y()), xytext=(5, 10), textcoords='offset points')
Kamil Sindi

2
Terima kasih @capitalistpug. Saya menemukan bahwa menambahkan kesejajaran horizontal membuat Anda lebih baik lagi. ax.annotate(str(int(p.get_width())), (p.get_x() + p.get_width(), p.get_y()), xytext=(-2, 4), textcoords='offset points', horizontalalignment='right') +1
DaveL17

32

Solusi yang juga menangani nilai negatif dengan format sampel float.

Masih membutuhkan penyesuaian offset.

df=pd.DataFrame({'A':np.random.rand(2)-1,'B':np.random.rand(2)},index=['val1','val2'] )
ax = df.plot(kind='bar', color=['r','b']) 
x_offset = -0.03
y_offset = 0.02
for p in ax.patches:
    b = p.get_bbox()
    val = "{:+.2f}".format(b.y1 + b.y0)        
    ax.annotate(val, ((b.x0 + b.x1)/2 + x_offset, b.y1 + y_offset))

nilai plot bar berlabel


0

Kapak memberi kita ukuran kotak.

x_position=##define a value
y_position=##define a value
for patch in ax.patches:
    b= patch.get_bbox()
    y_value=b.y1-b.y0
    ax.annotate(y_value, "x_position" , "y_position"))
plt.show()

untuk lebih jelasnya ::
Bbox (x0 = 3.75, y0 = 0.0, x1 = 4.25, y1 = 868.0)
Bbox (x0 = 4.75, y0 = 0.0, x1 = 5.25, y1 = 868.0)
Bbox (x0 = 5.75, y0 = 0.0 , x1 = 6.25, y1 = 1092.0)
Bbox (x0 = 6.75, y0 = 0.0, x1 = 7.25, y1 = 756.0)
Bbox (x0 = 7.75, y0 = 0.0, x1 = 8.25, y1 = 756.0)
Bbox (x0 = 8.75 , y0 = 0,0, x1 = 9,25, y1 = 588,0)
Bbox (x0 = 3,75, y0 = 868,0, x1 = 4,25, y1 = 3724,0)
Bbox (x0 = 4,75, y0 = 868,0, x1 = 5,25, y1 = 3528,0)
Bbox (x0 = 5.75, y0 = 1092.0, x1 = 6.25, y1 = 3948.0)
Bbox (x0 = 6.75, y0 = 756.0, x1 = 7.25, y1 = 2884.0)
Bbox (x0 = 7.75, y0 = 756.0, x1 = 8.25, y1 = 3024.0)
Bbox (x0 = 0.75, y0 = 4004.0, x1 = 1.25, y1 = 4396.0)
Bbox (x0 = 1.75, y0 = 3668.0, x1 = 2.25, y1 = 4060.0)
Bbox (x0 = 2.75, y0 = 3864.0, x1 = 3,25, y1 = 4060,0)

ini adalah keluaran dari patch.get_bbox () di program saya.
kita dapat mengekstrak detail kotak pembatas dari sini dan memanipulasinya untuk kebutuhan kita

Dengan menggunakan situs kami, Anda mengakui telah membaca dan memahami Kebijakan Cookie dan Kebijakan Privasi kami.
Licensed under cc by-sa 3.0 with attribution required.