簡體   English   中英

100% 堆積條形圖 - python (seaborn/matplotlib)

[英]100% stacked bar chart - python (seaborn/matplotlib)

我需要生成一個 100% 堆積條形圖,包括分布的百分比(沒有小數)或觀察次數。

我的數據集如下所示:

在此處輸入圖像描述

我需要生成一個不同的計算每月活動和遲到的數量:

在此處輸入圖像描述

然后使用第二個數據框生成我的 100% 堆積條形圖(應該看起來像這樣)

在此處輸入圖像描述

有沒有人有一個簡單的方法來做到這一點?

謝謝!!

您可以嘗試使用歸一化的value_counts()

(df.groupby('Date')['Status'].value_counts(normalize=True)
   .unstack('Status').plot.bar(stacked=True)
)

您可以使用下面的代碼生成以下圖表。 還請考慮閱讀答案,直到我解釋為什么水平條形圖可能更好。

在此處輸入圖像描述

我的數據集如下所示:

thermo_sensation_round 熱偏好
0 2 冷卻器
1 2 冷卻器
2 0 沒變
3 0 沒變
4 1 溫暖的

我使用以下代碼生成繪圖。 在代碼中,我正在執行以下步驟:

  1. 對數據進行分組,對條目進行計數,並對它們進行規范化
  2. 使用 Pandas 的函數.plot.bar(stacked=True)繪制數據
  3. 將圖例放在頂部
  4. 使用for循環將格式化文本添加到圖表中。 請注意,如果低於 10%,我不會打印百分比,您可以更改它。
  5. 使用tight_layout()使圖像居中。
    x_var, y_var = "thermal_sensation_round", "thermal_preference"
    df_grouped = df.groupby(x_var)[y_var].value_counts(normalize=True).unstack(y_var)
    df_grouped.plot.bar(stacked=True)
    plt.legend(
        bbox_to_anchor=(0.5, 1.02),
        loc="lower center",
        borderaxespad=0,
        frameon=False,
        ncol=3,
    )
    for ix, row in df_grouped.reset_index(drop=True).iterrows():
        cumulative = 0
        for element in row:
            if element > 0.1:
                plt.text(
                    ix,
                    cumulative + element / 2,
                    f"{int(element * 100)} %",
                    va="center",
                    ha="center",
                )
            cumulative += element
    plt.tight_layout()

水平堆積條形圖

使用水平條形圖是一個更好的主意,因為它更容易閱讀百分比。 請參見下面的示例。

在此處輸入圖像描述

要做到這一點非常簡單,您只需要將bar函數替換為barh 請注意,您需要在 text 函數中反轉 x 和 y 坐標。 請在下面找到代碼。

    x_var, y_var = "thermal_sensation_round", "thermal_preference"
    df_grouped = df.groupby(x_var)[y_var].value_counts(normalize=True).unstack(y_var)
    df_grouped.plot.barh(stacked=True)
    plt.legend(
        bbox_to_anchor=(0.5, 1.02),
        loc="lower center",
        borderaxespad=0,
        frameon=False,
        ncol=3,
    )
    for ix, row in df_grouped.reset_index(drop=True).iterrows():
        print(ix, row)
        cumulative = 0
        for element in row:
            if element > 0.1:
                plt.text(
                    cumulative + element / 2,
                    ix,
                    f"{int(element * 100)} %",
                    va="center",
                    ha="center",
                )
            cumulative += element
    plt.tight_layout()

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM