Inspiration
Central Florida food bank organizers have to decide where the next mobile pantry goes, and then defend it to boards and funders. Too often the answer is gut feel, the loudest partner, or a spreadsheet nobody else can follow. I wanted "why there?" to have a clear, honest, data-backed answer.
What it does
Beacon Neighborhood Action Desk maps 490 Census tracts across Orange, Seminole, Osceola, and Lake counties and labels each with a familiar place name. Organizers get a shortlist of high-poverty, low-access areas and a plain-English evidence card for each one, with every number shown next to its margin of error.
A machine learning check flags places where fewer households receive SNAP than similar areas would suggest, a possible spot for a sign-up event. A person always decides: organizers approve or challenge a recommendation with a reason, assign follow-up, and keep disagreements on the record. They can export a one-page decision brief for their board and a resident flyer. Nothing is sent or dispatched automatically.
How I built it
- Auto-cleaning pipeline (Python): one command rebuilds the tract table from raw ACS, USDA SNAP Retailer Access Map, and retailer files. It fixes encodings, strips extra Census header rows, standardizes tract IDs, turns placeholder codes into honest blanks, removes duplicates, validates one-to-one joins, and flags weak estimates from their margins of error. If a new data drop has missing or renamed columns, publishing stops and a review report is written for a person.
- Neighborhood mapping: TIGER tract polygons are overlaid on Census places and Orlando's official neighborhood boundaries to assign names, each with a High, Medium, or Low confidence rating.
- ML (supervised): ridge regression predicts each tract's expected SNAP participation from six non-SNAP factors, using 5-fold out-of-fold predictions. Its mean error is 5.6 percentage points, against 8.2 for a naive baseline, and R² is 0.50. A tract is only flagged when the shortfall is bigger than the Census margin of error plus the model's own typical error, which leaves 4 of 488 modeled tracts flagged.
- App: React + Vite + Leaflet, with 35 automated app tests and 18 Python tests.
Challenges
- Census data at the tract level is noisy: most estimates have wide margins of error, so I chose to show that uncertainty instead of hiding it.
- USDA "low access" counts SNAP-authorized stores, not just supermarkets, and there is no transportation data for Central Florida, so I didn't invent any.
- There is no ground-truth label for food need, so the model predicts SNAP participation and is framed as a screening signal, not proof.
What I learned
Trust comes from honesty. Showing error bars, caveats, and who decided what makes a recommendation easier to defend than a single confident score.
What's next
Pilot with local food bank partners, add verified pantry locations, and test against real outreach results.
Built With
- census-acs
- css
- geopandas
- javascript
- leaflet.js
- node.js
- numpy
- pandas
- python
- react
- scikit-learn
- tiger-line
- usda
- vite
