Most high school math students have come across the Traveling Salesman Problem. It’s a classic way to illustrate how complexity explodes factorially when you try to optimize a route between cities. Now imagine a similar problem—but with a moving graph, unpredictable demand, and golfers who get ornery if they don’t get their drinks in time.
Welcome to the Traveling Beer Girl Problem.
About ten years ago, I worked on an app called HappyTapp—and its slightly more chaotic sibling, Scan4Beer. The pitch was simple: you’re on a golf course, you want a beer, and instead of waiting for the beer cart to randomly roll by, you just tap your phone. A beer appears.From a UX perspective: brilliant. From a math and routing perspective: welcome to hell.
Golf courses are basically two loops: front nine, back nine. Add in paths, hazards, trees, maybe the occasional pond or desert, and now throw in 36+ player groups, all moving slowly and erratically across 18 holes.
Now assume all of them order drinks at once. You’ve just hit a real-world Traveling Salesman Problem with 36 moving targets. Except it's worse, because every action changes the map in real time. A greedy algorithm might have the beer girl head to the nearest group—but then she gets trapped in what I call the Cluster of Alcoholics Problem: a few heavy drinkers monopolizing the cart by being close and thirsty.
We tried a simple penalty function—prioritize those who’ve waited the longest. That helped avoid the cluster trap, but created whiplash: now she’s zooming across the course and back, repeatedly, chasing aging tickets. It’s fragile, non-generalizable, and infuriating to everyone.To make things even more delightful, some players never used the app at all. They just expected the beer cart to show up like always. So now we had to balance:
As with most real-world optimization problems, the answer wasn’t a single algorithm. It was a composable system—an ensemble of lightweight heuristics, stitched together by common sense.
Start with what the beer girl would normally do: drive the loop. Front nine, back nine, repeat. This is our base schedule. We know the general velocity of a cart (surprisingly consistent, by the way), so we can estimate where she’ll be at any given time if left undisturbed.
As orders come in, we assess whether the cart can make a diversion to a waiting group without diverging too far from the main route. This is a bounded cost function—we don’t allow massive detours, especially those that send her backward.
Unlike cities, golfers move. Slowly, yes—but unpredictably. So we don’t just use their current location, we also estimate their future location based on pace-of-play and current hole. This way, we avoid delivering to where someone was ten minutes ago.
When demand gets dense (i.e., more than ~8-10 orders in a single loop), we break the space into manageable segments. Think of the loop as a ring; now segment it into arcs. Each arc can be optimized independently using well-known closed-loop traversal heuristics.We simplify even further by projecting the loop into a linear space: a ring becomes a straight line, and we solve for shortest paths with wrap-around. This makes distance estimation and rerouting easier.
Because some golfers refuse to use the app (you know who you are), we also build in a passive sweep. The beer cart continues through under-served areas even if there are no active orders, mimicking its legacy behavior. This hybrid model satisfies the old-schoolers while still optimizing for real orders.
The Traveling Beer Girl Problem isn’t just a fun twist on the TSP. It’s a real-world demonstration of why perfect algorithms don’t survive contact with reality. Your targets move. Your inputs lie. Your customers get mad.But with a little domain knowledge, a handful of cheap heuristics, and a commitment to not over-optimize, you can build a system that keeps most people happy, most of the time.Even the ones who think yelling “beer girl!” from the fairway is still the best UX.
Next time you get a cold one mid-round, raise it to the backend logic no one sees—but everyone depends on.