Skip to content

Instantly share code, notes, and snippets.

@hdary85
Last active April 21, 2025 19:15
Show Gist options
  • Select an option

  • Save hdary85/7242d0efe153485fd743a6ac8b228ce1 to your computer and use it in GitHub Desktop.

Select an option

Save hdary85/7242d0efe153485fd743a6ac8b228ce1 to your computer and use it in GitHub Desktop.
import pandas as pd
import numpy as np
import matplotlib.pyplot as plt
def repartition_par_pourcentiles(values, pct_step=5):
"""
Calcule la répartition par tranche de population et renvoie bornes, effectifs et proportions.
"""
series = pd.Series(values).dropna().sort_values().reset_index(drop=True)
total = len(series)
n_steps = int(100 / pct_step)
edges = [i * pct_step / 100 for i in range(n_steps + 1)]
groups = pd.qcut(series, q=edges, duplicates='drop')
cats = groups.cat.categories
counts = groups.value_counts().sort_index()
low_bounds = [interval.left for interval in cats]
high_bounds = [interval.right for interval in cats]
proportions = (counts / total * 100).values
return pd.DataFrame({
'count': counts.values,
'proportion': proportions,
'threshold_low': low_bounds,
'threshold_high': high_bounds
})
if __name__ == '__main__':
df = pd.DataFrame({
'transactions': [5, 12, 7, 20, 15, 3, 30, 8, 14, 10]
})
pct_step = 5
stats = repartition_par_pourcentiles(df['transactions'], pct_step=pct_step)
print(stats)
# Graphe en pourcentages avec labels proportionnels
fig, ax = plt.subplots()
bars = ax.bar(range(len(stats)), stats['proportion'])
ax.set_xlabel('')
ax.set_ylabel('Proportion (%)')
ax.set_title(f'Répartition par tranches de {pct_step}%')
# Définir ticks et labels en fonction de la colonne 'proportion'
percent_labels = [f"{p:.1f}%" for p in stats['proportion']]
ax.set_xticks(range(len(stats)))
ax.set_xticklabels(percent_labels, rotation=45)
# Annotation : intervalle de valeurs pour chaque barre
for i, row in stats.iterrows():
label = f"{int(row['threshold_low']):,}-{int(row['threshold_high']):,}"
ax.text(i, row['proportion'] + 0.5, label,
ha='center', va='bottom', fontsize=8, rotation=90)
plt.tight_layout()
plt.show()
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment