1. The Word That Sounds Scarier Than It Is
Genetic algorithm. If you've never heard it, it sounds like a PhD thesis. If you have, someone probably told you it involves complicated crossover operators, mutation probabilities, and Pareto fronts. The reality is much simpler: a genetic algorithm is trial and error with a good memory.
Imagine you're cooking. You make a dish, taste it, and it's bland. Next time you add more salt. If it improves, you keep the change. If it gets worse, you go back. That's exactly what a genetic algorithm does — except instead of cooking dinner, it's designing an airplane wing. And instead of doing it once, it does it 10,000 times in an hour.
The term "genetic" comes from biology. Darwin observed that animals with favorable traits survive and reproduce, passing those traits to offspring. Genetic algorithms copy this mechanism: create a population of solutions, select the best ones, cross them to generate "child" solutions, and repeat. Generation after generation, the solutions improve.
You don't need to know how to code to understand how they work. You just need to be hungry. Let's design the perfect pizza.
2. The Perfect Pizza: An Optimization Problem Disguised as Dinner
You have three variables for your pizza: crust thickness (1 to 10), cheese amount (1 to 10), and oven temperature (150 to 300 degrees Celsius). Your goal: the most delicious pizza possible. This is an optimization problem with 3 variables.
A brute-force approach would test ALL combinations. That's 10 × 10 × 151 = 15,100 different pizzas. Assuming 20 minutes per pizza, you'd need 210 days without sleep. And that's with just 3 variables. With 10 variables, the number of combinations explodes past what any computer could test. This is called the curse of dimensionality.
The genetic algorithm takes a much smarter approach. Instead of testing all combinations, it starts with a small group of random pizzas, tests them, learns from the results, and generates new pizzas by mixing the best features of the previous ones. It's like instead of reading every book in a library, you talk to the most well-read people and take their recommendations.
3. Population and Chromosomes: Your First 10 Pizzas
The algorithm begins by generating 10 random pizzas. Each pizza is what we call an individual, and the set of 10 pizzas is the population. Each individual has a chromosome, which is nothing more than a list of numbers. That simple:
- Pizza 1: [3, 8, 220] → thin crust, lots of cheese, medium temperature
- Pizza 2: [9, 2, 300] → thick crust, little cheese, oven at max
- Pizza 3: [1, 10, 180] → ultra-thin crust, cheese overload, low oven
- And so on until 10.
That list of three numbers is the chromosome. In real engineering, the chromosome might have 50 numbers representing the curvature of a wing, the thickness of a material, or the angle of a turbine blade. But the principle is identical: a list of values that defines a candidate solution.
The first 10 pizzas will probably be terrible. Most will be burnt, raw, or with some inedible combination of ingredients. But one, by pure chance, will be slightly less awful than the others. And that's where the magic begins.
4. Selection: Let the Best Pizzas Survive
Once you've baked all 10 pizzas, you taste them and score each from 1 to 10. The top 4 survive. The other 6 go in the trash (or to the office break room). This process is called tournament selection.
The name sounds technical but the concept isn't: you organize a "tournament" where you pick a random group (say, 3 pizzas out of the 10) and the one with the highest score wins and advances to the next round. Repeat until you have enough winners. It's like a talent show but with more pepperoni.
In engineering terms, tournament selection is preferred because it doesn't require sorting the entire population and because it lets you control selection pressure: a large tournament (picking 5 instead of 3) means the best ones almost always win and the search becomes more intensive but less exploratory. A small tournament (2) maintains more diversity but takes longer to converge.
Here's the pseudocode for tournament selection in Python, so you can see how absurdly simple it is:
def tournament(population, k=3):
contestants = random.sample(population, k)
winner = max(contestants, key=lambda p: p.score)
return winner
# Repeat until you have N parents for the next generation
parents = [tournament(population, k=3) for _ in range(N)]
That's it. That's selection. Pick a few at random, keep the best one. Repeat. Zero magic, zero artificial intelligence, pure logic.
5. Crossover: When Two Pizzas Love Each Other Very Much
You now have your 4 survivors. Next, you need to create the next generation. You take two parents and cross them to produce a child. The simplest mechanism is called single-point crossover:
Pizza A: [3, 8, 220] (thin crust, lots of cheese, 220°C)
Pizza B: [7, 5, 180] (thick crust, medium cheese, 180°C)
Pick a random cut point — say, between the first and second variable — and combine:
Child 1: [3, 5, 180] — thin crust from A, cheese and temperature from B
Child 2: [7, 8, 220] — thick crust from B, cheese and temperature from A
It's like taking your grandmother's pasta recipe and a chef's sauce recipe and combining them. Sometimes you get a disaster. Sometimes you get something neither one would have imagined. That's the beauty of it.
In more sophisticated versions like SBX (Simulated Binary Crossover) used in NSGA-II, instead of directly copying values, you compute a weighted average of the parents controlled by a parameter that determines how far the children stray from the parents:
def crossover(parent1, parent2, eta=20):
child1, child2 = parent1[:], parent2[:]
for i in range(len(parent1)):
if random.random() < 0.5:
if random.random() <= 0.5:
beta = (2 * random.random()) ** (1 / (eta + 1))
else:
beta = (1 / (2 * (1 - random.random()))) ** (1 / (eta + 1))
child1[i] = 0.5 * ((1 + beta) * parent1[i] + (1 - beta) * parent2[i])
child2[i] = 0.5 * ((1 - beta) * parent1[i] + (1 + beta) * parent2[i])
return child1, child2
With high eta, children stay close to the parents (you exploit what you already know). With low eta, children explore new territory. Like everything in engineering: it's about balance.
6. Mutation: The Necessary Dash of Madness
If all you do is cross the best solutions, you risk getting stuck. Imagine that by pure chance, none of your initial pizzas contain oregano. No matter how many generations pass, you'll never discover oregano because it was never in the population's DNA. You need a mechanism that introduces new variety.
Enter mutation. Occasionally (typically 5-10% of the time), you take a child's value and tweak it slightly at random. The child [3, 5, 180] might mutate to [3, 5, 185]. Or to [3, 7, 180]. Small changes, but enough to explore combinations nobody had tried before.
The mutation rate is a delicate balance. Too low and you don't explore enough. Too high and your algorithm becomes pure random search, losing everything learned in previous generations. It's like changing one ingredient in a recipe each time you cook. Change too little and you improve gradually. Change everything at once and you'll never know what worked and what didn't.
In practice, mutation probability is set to 1/n, where n is the number of variables. For our 3-variable pizza, each variable has a 33% chance of mutating per generation. For an aircraft wing with 50 design variables, each has a 2% chance. Many small mutations, not a few big ones.
7. The Train Schedule Problem: When the Human Brain Throws in the Towel
Okay, pizza is fun. But nobody gets paid to design pizzas with genetic algorithms. Let's look at a real problem: scheduling a train network.
Imagine 50 trains competing for 200 time slots in a day. Each train has a route, a speed, a priority, and a minimum headway between departures. You want to maximize the number of passenger connections between trains (so people can transfer) and minimize cumulative delays. This problem has more possible combinations than atoms in the observable universe.
A human planner might produce a decent schedule for 10 trains in a week. But for 50 trains with 200 time slots, the interactions are so complex that no human — not even a team of humans — can find the optimal solution. There are simply too many possibilities.
The genetic algorithm frames it like this: each chromosome is a list of 50 integers, where each integer represents the time slot assigned to each train. For example, [14, 87, 3, 156, ...] means: train 1 departs at slot 14, train 2 at slot 87, train 3 at slot 3, and so on. The fitness function (the pizza score) calculates how many connections are achieved and how much delay is generated.
With 200 generations and a population of 100 schedules, the algorithm evaluates 20,000 different timetables — each one testing different combinations of slot assignments — and converges toward solutions no human would have discovered. And it does this in minutes. It's not the perfect solution (that's practically impossible to find), but a near-optimal one: roughly 95-98% as good as the theoretical optimum.
8. Why It Works: Survival of the Building Blocks
There's a mathematical reason genetic algorithms work, called the schema theorem. But don't worry — we'll explain it without a single equation.
Imagine that in the train scheduling problem, you discover that commuter trains departing in odd-numbered slots tend to connect better with long-distance trains. That pattern ("odd slot for commuter trains") is what we call a schema: a partial solution that works well regardless of the other variables.
Genetic algorithms are extremely good at detecting these schemas. When two parents share a good chunk of a solution, crossover tends to preserve it in their children. And when that chunk appears in multiple high-scoring individuals, selection tends to multiply it throughout the population. It's a process of propagation of good partial ideas.
The schema theorem proves mathematically that short, low-order schemas with above-average performance receive an exponentially increasing number of copies in successive generations. Translation: good ideas go viral within the population. What works gets copied. What doesn't goes extinct.
It's Darwinian evolution inside a computer. And it works for the same reason nature has produced eyes, wings, and brains: because accumulating small improvements over many generations yields astonishing results.
9. When NOT to Use Genetic Algorithms
Genetic algorithms aren't a universal tool. There are situations where using one is like killing a mosquito with a sledgehammer. Here are three rules for knowing when to look elsewhere:
Rule 1: If you can compute the gradient, use gradient descent. If your problem has a differentiable function (you can calculate which direction improves fastest), methods like gradient descent or L-BFGS are vastly faster. A genetic algorithm explores blindly; gradient descent follows the steepest slope. If you're on a foggy hill, the genetic algorithm stumbles around; gradient descent says "downhill is that way."
Rule 2: If the problem is small, use brute force. For problems with 4 or 5 variables and few possible values, evaluating all combinations is faster than setting up the entire genetic algorithm scaffolding. Don't use a rocket to go to the corner bakery.
Rule 3: If constraints are very strict, use MILP or SAT solvers. If all your variables are discrete and you have constraints like "if A then not B," integer linear programming (MILP) or satisfiability (SAT) solvers are unbeatable. Genetic algorithms can handle constraints, but they struggle. Don't ask a marathon runner to play chess.
Genetic algorithms shine in the sweet spot: problems with many variables, expensive evaluation functions (like CFD simulations that take hours), multiple conflicting objectives, and search spaces riddled with local optima. That's where evolution beats differential calculus.
10. From Pizza to the Real World: What We've Learned
We've traveled from pizza to train schedules. Along the way, you've learned the five ingredients of any genetic algorithm: population (a group of solutions), selection (keep the best ones), crossover (combine the good ones), mutation (explore new things), and evaluation (knowing which one is better).
The most beautiful part is that the algorithm knows nothing about the problem it's solving. The same code that designs the perfect pizza can design an airplane wing, organize train schedules, or find the optimal mix of composite materials. Only the evaluation function changes. The evolutionary engine is exactly the same.
At MaterialTech Labs we use genetic algorithms daily. We optimize surf fins with NSGA-II (balancing speed, maneuverability, and weight), design carbon fiber layups minimizing weight and maximizing stiffness, and search for aerodynamic profiles no human engineer would have drawn by hand. Evolution, inside a computer, finds solutions that human intuition overlooks.
Next time you hear "genetic algorithm," don't think of formulas or PhD theses. Think of a patient cook who tries, discards, mixes, and tries again until the dish comes out perfect. It's trial and error. On steroids.
Want to apply genetic algorithms to your engineering challenges?
At MaterialTech Labs we integrate evolutionary algorithms with CFD simulation, structural analysis, and parametric design. We optimize what seemed impossible to optimize. From surf fins to aircraft wings.
Talk to us