Leçon 4 sur 8
Unité · Le circuit
L'écart s'ouvre avant que le référencement ne soit fait
Les cas avec handicap signalé aboutissent à 26,7 % contre 46,2 %. L'écart n'est pas à la porte du service — le consentement est identique à 89 % et 88,5 % — il s'ouvre à la porte où un travailleur social décide de faire ou non le référencement.
Trouvez la porte, non le total
Un taux d’aboutissement de bout en bout de 43,8 % vous dit que le circuit fuit. Il ne dit pas où, et les quatre portes perdent des quantités très différentes.
import pandas as pd
referrals = pd.read_csv("protection-referrals-2024.v1.csv")
def cascade(frame):
consented = frame[frame["consent_to_refer"]]
made = consented[consented["referral_made"]]
accepted = made[made["referral_accepted"]]
reached = accepted[accepted["days_to_first_service"].notna()]
return pd.Series({
"n": len(frame), "consented": len(consented), "made": len(made),
"accepted": len(accepted), "reached": len(reached),
})
totals = cascade(referrals)
print(totals)
print("\nloss at each gate:")
print(f" consent: {1 - totals['consented'] / totals['n']:.1%}")
print(f" referral: {1 - totals['made'] / totals['consented']:.1%}")
print(f" accepted: {1 - totals['accepted'] / totals['made']:.1%}")
print(f" service: {1 - totals['reached'] / totals['accepted']:.1%}")
library(dplyr)
referrals |> summarise(
n = n(),
consented = sum(consent_to_refer),
made = sum(consent_to_refer & referral_made),
accepted = sum(referral_made & referral_accepted),
reached = sum(referral_accepted & !is.na(days_to_first_service))
)
| Porte | Perte à ce point |
|---|---|
| Consentement | 11,5 % — une décision, non une perte |
| Référencement effectué | 30,3 % |
| Référencement accepté | 33,7 % |
| Service atteint | 5,3 % |
Les deux portes du milieu perdent presque tout. Une fois le référencement accepté, 94,7 % des cas atteignent le service — le bout récepteur fonctionne. La défaillance est en amont : un référencement jamais fait, et un référencement fait puis refusé.
Ce sont deux problèmes différents avec deux responsables différents. Un taux d’aboutissement unique masque lequel vous avez, et un programme lisant 43,8 % investirait raisonnablement dans le service qui n’est pas le goulot.
Quel service, et quelle zone
by_service = referrals.groupby("service_requested").apply(cascade,
include_groups=False)
by_service["completion"] = by_service["reached"] / by_service["consented"]
print((by_service["completion"] * 100).round(1).sort_values())
referrals |>
summarise(consented = sum(consent_to_refer),
reached = sum(referral_accepted & !is.na(days_to_first_service)),
.by = service_requested) |>
mutate(completion = reached / consented) |> arrange(completion)
| Service | Aboutissement | Référencement fait | Accepté |
|---|---|---|---|
| Appui aux moyens de subsistance | 20,7 % | 49 % | 47 % |
| Juridique | 30,0 % | 61 % | 50 % |
| Sécurité et protection physique | 33,8 % | 61 % | 58 % |
| Psychosocial | 53,2 % | 77 % | 72 % |
| Santé | 57,6 % | 81 % | 76 % |
L’appui aux moyens de subsistance aboutit au tiers du taux de la santé, et il échoue également aux deux portes du milieu — la moitié des référencements ne sont jamais faits et la moitié de ceux qui le sont sont refusés. C’est la signature d’un service connu pour être saturé : les travailleurs sociaux cessent d’y référer parce qu’ils connaissent la réponse.
Les zones vont de 29,7 % à 53,8 %, un écart assez large pour agir et assez étroit pour qu’aucune zone n’aille bien.
L’écart qui compte
disability = referrals["disability_reported"].isin([True, "true", "Yes"])
no_disability = referrals["disability_reported"].isin([False, "false", "No"])
for label, mask in [("reported", disability), ("not reported", no_disability)]:
row = cascade(referrals[mask])
print(f"{label:14} n={row['n']:>5} "
f"consent {row['consented'] / row['n']:.1%} "
f"made {row['made'] / row['consented']:.1%} "
f"accepted {row['accepted'] / row['made']:.1%} "
f"→ {row['reached'] / row['consented']:.1%}")
referrals |>
mutate(disability = disability_reported %in% c("true", "Yes")) |>
summarise(n = n(), consented = sum(consent_to_refer),
made = sum(consent_to_refer & referral_made),
accepted = sum(referral_made & referral_accepted),
reached = sum(referral_accepted & !is.na(days_to_first_service)),
.by = disability)
| n | Consentement | Référencement fait | Accepté | Aboutissement | |
|---|---|---|---|---|---|
| Handicap signalé | 227 | 89,0 % | 54,5 % | 56,4 % | 26,7 % |
| Non signalé | 1 623 | 88,5 % | 71,9 % | 67,3 % | 46,2 % |
Le consentement est identique — 89,0 % contre 88,5 %. Les personnes en situation de handicap sont exactement aussi disposées à être référées.
L’écart s’ouvre aux deux portes que contrôle le système de services. Un référencement est fait pour 54,5 % d’entre elles contre 71,9 %, et accepté pour 56,4 % contre 67,3 %. À la porte du service, la différence s’est composée en dix-neuf points.
Localiser l’écart à une porte précise transforme une observation en action. « Les résultats sont plus mauvais pour les personnes en situation de handicap » est un constat sur lequel personne ne peut agir. « Les travailleurs sociaux font un référencement pour 55 % d’entre elles contre 72 %, et les services receveurs en acceptent 56 % contre 67 % » nomme deux conversations avec deux parties nommées.
Avant de le publier
Trois vérifications, et la première changera vos nombres.
La colonne handicap a quatre valeurs. Une zone a saisi Yes et No au lieu de
true et false, si bien qu’un groupement naïf produit quatre catégories, dont
deux trop petites pour être interprétées et une silencieusement supprimée par un
filtre booléen.
print(referrals["disability_reported"].value_counts(dropna=False))
referrals |> count(disability_reported)
Le handicap est auto-déclaré et sous-déclaré. 227 sur 1 850 font 12,3 %, en dessous de la plupart des estimations de population. L’écart est réel ; le dénominateur est un groupe qui a déclaré, et les personnes qui ne l’ont pas fait sont comptées dans le groupe de comparaison. Cela biaise l’écart vers le bas — 19 points sont donc un plancher.
Vérifiez la taille des cellules avant de désagréger davantage. Handicap par zone par service est exactement le tableau à quatre entrées que la leçon précédente a refusé de publier.
Rapportez les portes, non le total
Referral pathway, 1,638 consenting cases
Referral made 69.7%
Accepted, of those made 66.3%
Reached service, of accepted 94.7%
End to end, of consenting 43.8%
The pathway fails upstream. Once a referral is accepted 94.7% of cases
reach a service; the losses are at referral-making and acceptance.
Cases reporting a disability: 26.7% complete against 46.2%. Consent is
identical (89.0% and 88.5%); the gap is entirely at referral-making
(54.5% against 71.9%) and acceptance (56.4% against 67.3%).
Disability is self-reported by 12.3% of cases. Non-disclosure places some
people in the comparison group, so the gap is a lower bound.
La suite
Le circuit s’arrête quand un cas atteint un service. Ce qui se passe ensuite est un dossier que quelqu’un doit porter, et l’unité suivante porte sur le registre qui enregistre qui en porte combien.