It's Too Noisy! How to Adjust Finish Times for Random Race Noise

By Lambert Chu

Odds are officially gone! Now, it takes more races to evaluate how competitive your horses really are, especially newly-bred ones. Even though I think this is beneficial long-term to the ZED ecosystem, it can be frustrating to deal with a game of discovery that can be time-consuming and pricey.

Goodbye, old friend. Shoutout to Balgood Farms for the A+ meme.

As a result, I believe speed data is now more important than ever. If we’re able to understand how our horses stack up against all of the other horses in the game in as few races as possible, it’ll save us all a ton of time and headaches. The goal is to gain more information in fewer races to manage our horses as efficiently as possible.

In this blog post, we’ll make some adjustments to speed data to take it to another level. We’ll break down a strange phenomenon that I believe has been polluting the quality of speed data: race noise.

What is Race Noise?

Have you ever seen a race where the entire field ran especially fast or slow? Some of you seasoned ZED heads have probably picked up on this already! I believe this is actually randomized “noise” that ZED introduces to some races, so that finish times are less consistent and harder to predict from race to race. In theory, this noise should make the game more interesting and more difficult to crack.

For example, let’s look at one race that ran especially fast. This one was a Class III, 1800m race that occurred in July before the new fatigue update, so we know that that couldn’t have played a role yet.

For the sake of this analysis, we’ll only use race stats from before the fatigue update.

For reference, the global average time for 1800m is 107.8 seconds and global standard deviation is 1.7.

New Zealand Oaks (Class III, 1800m)

The average finish time for all horses in this race was 102.2 seconds, which is nearly 6 seconds faster than the global average of 107.8 seconds

Luna Nueva ran the slowest time of 104.3s, which is actually two standard deviations faster than average. The winner, I Am A Stud, ran 10 seconds faster than average, which is absurd 6 standard deviations away!

I mean, this horse certainly is a stud, but the odds of running a time that fast by chance is VERY low. On top of that, it’s virtually impossible for every single horse to run > 2 standard deviations faster than average, just by chance alone.

Something seems funky about that race, don’t you think?

On the flip side, let’s take a look at a race that ran especially slow. This is another Class III, 1800m race that ran just a few days later in July (before the fatigue update).

Racing In The Life Artois (Class III, 1800m)

The average finish time was 114 seconds, which is 6 seconds (over 3 standard deviations!) slower than average.

In fact, the 12th place horse in the “fast” New Zealand Oaks race ran 8 seconds faster than the winner of the “slow” Artois race.

That 8-second gap is just massive. Since there’s been a history of races like these, there must be some other random factor involved that causes the entire field to run so fast or slow.

How Common is Race Noise?

After diving into two extreme examples of race noise, we’ll now take a broader view at just how impactful it is across all races.

To do this, we’ll follow the same approach as above. We compare the average time of all horses in each race - which we’ll call the race average -  with the global average time for that race’s distance. For example, suppose the average time for all horses in a 2000m race is 117.9 seconds. The global average for 2000m races is 119.9 seconds, so the race noise in this case is -2 seconds.

After calculating the noise for all races in the history of ZED, we get a distribution that looks like this:

Wow… it looks so clean!

The predicted race noise is centered at exactly 0 and is almost perfectly symmetrical. After seeing this plot, I’m even more inclined to believe that this is how ZED is introducing randomness to races.

It’s worth noting that 30% of all races have a race average that is equal to the global average (which means they don’t have any race noise), and most races have somewhere between -2 and +2 seconds of noise. It’s very rare for race noise to exceed 3 seconds in either direction, so the two earlier examples of -6 seconds and +6 seconds were truly extreme cases.

Removing Race Noise

Random noise might make races more interesting and harder to crack, but I don’t want it messing up our precious speed data anymore. Let’s try to get rid of it!

To do this, we will “re-scale” all finish times, such that the average time of each race is equal to the global average. As a result, we multiply each finish time in the race by a constant multiplier, which shifts all times closer to the global average.

By using these adjusted times, the average horse in every race is the same, which allows us to fairly compare finish times across all races. We are finally comparing apples to apples!

To see it in action, here are the adjusted times from the earlier examples:

BOOM! The average race times aren’t so far apart anymore. Now we see that the finish times between these two races can be compared much more reasonably.

For example, it makes sense that The Bold and Brave, the winner of the slow race, is ranked highly in terms of adjusted times for finishing well ahead of the middle of the pack.

I Am A Stud is still well-rewarded for having a dominant time. His adjusted time is 3 standard deviations faster than average, which is very fast but not as ridiculous as 6 standard deviations.

How Is This Useful?

Since race noise is quite predictable, it shouldn’t impact a horse’s speed curve that much IF it has raced many times; all of the random noise should cancel out after, say, 20 races.

The problem is that most of us wouldn’t want to race our horses 20 times per distance if they aren’t winning! As a result, using adjusted times to remove noise should be tremendously helpful for evaluating horses with a small sample size of races.

To see this in action, let’s take a look at the horse Zeltic Ocean. At the time of writing, it only has 4 races under its belt at 2000m. Its finish times were scattered widely: 108.6s, 119.6s, 120.9s, and 121.6s.

For those keeping score at home, that would be one exceptionally fast time, one average time, and two below average times. This results in two distinct clusters of finish times, which can make for an ambiguous evaluation:

Can the real Zeltic Ocean please stand up? We can get a better idea of how it runs by using adjusted times instead.

It turns out that its exceptionally fast time came from a fast race (unsurprisingly). However, its slower times came from slow races! That makes plenty of sense, since it finished either 1st or 2nd in all of these races.

After plotting adjusted times, it’s much more obvious that Zeltic has been a very fast runner at 2000m, which is backed soundly by odds and flames data:

Previously, the finish time data was actually misleading because it only included a sample of 4 races. With the adjustments, it is now highly consistent with other data observations.

Next Steps

Adjusted finish times should be an improvement over raw finish times. They are most useful when evaluating horses that have a small sample size of races, as well as for interpreting insanely fast/slow races like the examples from the beginning of the post.

By using adjusted times instead of raw times, we will have a more reliable foundation to use down the road for calculating more advanced metrics and studying other problems.

For example, we would like to calculate the average ability of horses, which would have big implications for predicting breeding outcomes. By using adjusted times, we should arrive closer to true average ability than using raw times.

But we have to remember a very important caveat: all of this analysis was done using data from BEFORE the fatigue update! We can only isolate the effect of race noise before fatigue started messing with finish times.

However, if we’re able to remove the random effects of race noise, we now have a better shot at isolating the effects of fatigue, which has been one of the biggest question marks in the game following the recent update.

That will be one of the next major research problems we’ll tackle, so stay tuned for more content coming your way!