'How to make a horizontal stacked histplot based on counts?

I have a df which represents three states (S1, S2, S3) at 3 timepoints (1hr, 2hr and 3hr). I would like to show a stacked bar plot of the states but the stacks are discontinous or at least not cumulative. How can I fix this in Seaborn? It is important that time is on the y-axis and the state counts on the x-axis.

enter image description here

Below is some code.

data = [[3, 2, 18],[4, 13, 6], [1, 2, 20]]
df = pd.DataFrame(data, columns = ['S1',  'S2', 'S3'])
df = df.reset_index().rename(columns = {'index':'Time'})
melt = pd.melt(df, id_vars = 'Time')

plt.figure()
sns.histplot(data = melt,x = 'value', y = 'Time', bins = 3, hue = 'variable', multiple="stack")

EDIT: This is somewhat what I am looking for, I hope this gives you an idea. Please ignore the difference in the scales between boxes...

enter image description here



Solution 1:[1]

If I understand correctly, I think you want to use value as a weight:

sns.histplot(
    data=melt, y='Time', hue='variable', weights='value',
    multiple='stack', shrink=0.8, discrete=True,
)

enter image description here

Solution 2:[2]

This is pretty tough in seaborn as it doesn't natively support stacked bars. You can use either the builtin plot from pandas, or try plotly express.

data = [[3, 2, 18],[4, 13, 6], [1, 2, 20]]
df = pd.DataFrame(data, columns = ['S1',  'S2', 'S3'])
df = df.reset_index().rename(columns = {'index':'Time'})
# so your y starts at 1
df.Time+=1

melt = pd.melt(df, id_vars = 'Time')
# so y isn't treated as continuous
melt.Time = melt.Time.astype('str')

Pandas can do it, but getting the labels in there is a bit of pain. Check around to figure out how to do it.

df.set_index('Time').plot(kind='barh', stacked=True)

enter image description here

Plotly makes it easier:

import plotly.express as px
px.bar(melt, x='value', y='Time', color='variable', orientation='h', text='value')

enter image description here

Sources

This article follows the attribution requirements of Stack Overflow and is licensed under CC BY-SA 3.0.

Source: Stack Overflow

Solution Source
Solution 1
Solution 2 Chris