MLB Player Analytics Engine
2025A player similarity search tool I built for the 2025 SABR Analytics Conference, focused on finding MLB players with similar statistical profiles.
I built this project for the 2025 SABR Analytics Conference, which I attended through a sponsorship from Major League Baseball. The idea came from a common scouting question: given a player's statistics, who else in the dataset plays similarly? Teams use player comparisons when evaluating talent, building projections, and making decisions about player value. I wanted to build a smaller version of that process and make each step easy to follow.
The project is a Python notebook that uses pandas for data processing and scikit-learn for the modeling. It takes a CSV of player statistics, split into three groups: hitting, batted-ball, and swing metrics.
Hitting statistics include batting average, slugging, walk rate, and strikeout rate. Batted-ball metrics include exit velocity, launch angle, and barrel rate. Swing metrics include bat speed and attack angle. I wanted to use all three groups because looking at a player's overall profile gives a more useful comparison than relying on a single statistic.
Method
The pipeline starts by handling missing values using the median, then standardizes the features so that statistics with larger numerical ranges do not dominate the comparison.
For similarity, I implemented both cosine similarity and inverse Euclidean distance. You can select a player, choose a metric, and retrieve the ten closest matches in the dataset.
- 01Read
- 02Fill
- 03Scale
- 04Rank
I also added optional K-Means clustering to group players with similar statistical profiles. The number of clusters is selected using the elbow method, and PCA plots help visualize how the groups are distributed.
I used these plots to explore whether different types of hitters, such as contact hitters and three-true-outcomes hitters, formed distinct groups.
Outliers
One decision I spent more time on was how to handle outliers. A common preprocessing step is to remove extreme values before fitting a model, but in baseball, some of the most interesting players are outliers precisely because of their performance.
Rather than automatically removing them, I looked at how those players affected the results and decided to keep them in the dataset.
I wanted the similarity results to be something a scout could actually look through and understand. Keeping the pipeline relatively simple also makes it easier to see how the data is processed and why two players end up being matched.