ML Lab
I trained two scikit-learn models on the Gen 1–3 Pokédex — 386 Pokémon, six base stats each. One model predicts Base Stat Total from physical and categorical traits. The other classifies legendary status from the six stats alone. Neither is impressive by production ML standards, but both do something non-trivial with a small, weird dataset, and building them taught me more about feature engineering than most tutorials do.
BST Regressor
R² 0.59 ± 0.06Predicts a Pokémon's Base Stat Total from height, weight, generation, and type — no stats used. R² ≈ 0.59 on cross-validation.
Feature importances
Predicted vs actual BST
Each dot is one Pokémon. Points above the dashed line are over-predicted; below are under-predicted.
Learning curve
Legendary Classifier
F1 0.83 ± 0.12Classifies legendary status from the six base stats alone, with no categorical features. F1 ≈ 0.83 on cross-validation — good, given only 15 legendaries in the training set.
Feature importances
Confusion matrix
Only 15 of 386 Pokémon are legendary — a 4% class rate. With that imbalance, recall matters more than accuracy: a model that predicted "never legendary" would score 96% accuracy but 0% recall.
Learning curve
Training code is in scripts/train-models.py in the repo. The models are pickled and served via a Vercel Python runtime function at api/predict.py. Cold start is slow (~20s on first request); warm requests are under 100ms. github.com/jleo28/pokedex-plus