
This is part 5 of my 12-part series documenting what I learned in “Technovate Thinking,” a course I took at business school.
The theme for Session 3 was “Algorithms.” The pre-class assignment was to represent a bubble sort algorithm as a flowchart and implement it in Scratch.
I’ll be honest — I’d heard the name “bubble sort” before, but I’d never actually drawn a flowchart for one and turned it into a program. Even with my long IT infrastructure background, building an algorithm “with my own hands” was an experience I’d had surprisingly few of. In infrastructure work, sorting is something databases and libraries just handle for you.
- 1 Why Bother Learning “the Most Inefficient Sort”?
- 2 The Nested Loop Structure — The Outer Loop Controls “How Many Passes,” the Inner Loop Controls “What Gets Compared”
- 3 A Single Flag Dramatically Changes Efficiency — Basic vs. Improved Versions
- 4 The Gap Between “Being Able to Draw a Flowchart” and “Writing a Working Program”
- 5 “Correct Algorithm” and “Good Algorithm” Are Two Different Things
- 6 From “You Can Use It Without Knowing How It Works” to “You Can Make Judgments Because You Know How It Works”
- 7 Some Understanding Can Only Be Gained by Getting Your Hands Dirty
- 8 This Assignment Became the Foundation for What Came Next
- 9 Next Up: Designing E-Commerce Recommendations — Applying Algorithms to Business
- 10 Books Referenced in This Post
Why Bother Learning “the Most Inefficient Sort”?
Bubble sort works by comparing two adjacent numbers and swapping them if they’re in the wrong order — repeating this over and over. It’s the simplest and often called the most inefficient sorting algorithm.
You’d almost never use bubble sort in practice. Behind a database’s ORDER BY or Python’s sorted() function, much faster sorting algorithms are at work. So why bother learning it?
The answer: “Because its simplicity strips the algorithm’s structure bare.” It contains all the fundamental elements of programming — loops, conditional branching, and variable management. With no extra complexity to get in the way, you can confront the design philosophy of algorithms head-on. This assignment was built precisely for that experience.
The Nested Loop Structure — The Outer Loop Controls “How Many Passes,” the Inner Loop Controls “What Gets Compared”
The structure of bubble sort is a nested loop — an outer loop and an inner loop.
The outer loop controls “how many passes to make through the entire array.” With each pass, the smallest (or largest) value moves to its final position. The inner loop repeats the process of “comparing adjacent pairs and swapping.” With each pass, the comparison range narrows — because the already-sorted portion doesn’t need to be checked again.
When you map it as a flowchart, it produces a remarkably clean structure composed of nothing but a nested loop and conditional branching. I thought it was the perfect subject for visually understanding “what an algorithm is.”
That said, “clean” and “easy” are two different things. A nested loop means you need to manage two indices simultaneously — which pass you’re on and which element you’re currently looking at. Each time the outer loop advances one pass, the inner loop’s range changes. This sensation of “the range shifting” was something I could grasp at the flowchart stage but became a source of confusion when actually writing the program.
A Single Flag Dramatically Changes Efficiency — Basic vs. Improved Versions
For the assignment, I first built the basic version, then the improved version. Comparing the two side by side produced the biggest insight of this session.
The basic version is brute force. Even if the data is already sorted, it dutifully completes every pass. You end up with “the sort is already done, but it’s still running comparisons.”
In the improved version, I added a single “swap occurred” flag. If no swaps happen during an inner loop pass, it concludes “sorting is complete” and exits the loop early.
The core operation is the same — comparing adjacent elements and swapping. But with just one flag, best-case efficiency improves dramatically. When the data is already sorted, the basic version faithfully runs every comparison, while the improved version detects “zero swaps” on the first pass and terminates immediately.
Computational complexity had come up repeatedly in class, but honestly, textbook explanations alone hadn’t clicked for me. It was only when I placed two flowcharts side by side and saw “this one change makes this much difference” that the efficiency gap landed not as a formula but as a gut feeling.
The Gap Between “Being Able to Draw a Flowchart” and “Writing a Working Program”
What I thought I understood from the flowchart looked completely different when I went to code it. This gap between “understanding” and “doing” was the most striking thing I felt during this assignment.
First, the swap operation. Intuitively, “swap A and B” seems straightforward, but in a program it doesn’t work that way. The moment you assign B’s value to A, A’s original value is gone. You need a temporary variable and must execute “save → overwrite → restore” in the correct order, all three steps. It looks trivial in a flowchart, but getting the order wrong by even one step breaks everything.
Next, index management. Advancing through elements while tracking “which element am I currently looking at?” — in bubble sort, you’re managing two indices simultaneously (inner and outer), which raises the complexity a notch. The inner loop’s range narrows with each outer loop pass. Hard-coding a fixed value here leads to a frustrating bug: “for some reason, the last few numbers never get sorted.”
Even trickier is the “1-indexed vs. 0-indexed” problem. Different programming environments start list numbering differently. If the flowchart and the implementation use different starting numbers, you end up referencing a non-existent index — the classic off-by-one error. This is reportedly the trap beginners fall into most often.
Looking at a flowchart, you can understand the logic. But when converting it to code, a stream of decisions pours in: “Which block should this conditional branch go inside?” “Where should I initialize this variable?” This assignment reinforced that there’s still a gap between “being able to draw a flowchart” and “writing a working program”. And the only way to close that gap is to get your hands dirty through trial and error.
“Correct Algorithm” and “Good Algorithm” Are Two Different Things
Placing the basic and improved versions side by side, the core operation is identical. Both sort correctly. Same result. But “goodness” is determined by whether you’ve engineered out the waste.
This distinction between “correct” and “good” isn’t limited to programming. The same applies to business process design. Take an approval workflow, for example. Routing every request through manager → director → executive in three stages is “correct.” But if you add logic to vary the approval route based on the dollar amount, the vast majority of requests can be processed much faster. The core operation (approving) is the same, but “where you introduce the optimization” changes efficiency entirely.
One flag in bubble sort corresponds to one branching condition in an approval workflow. The scale differs, but the thinking is the same. An algorithm’s “goodness” is the design ingenuity of solving the same problem in fewer steps. This is a sensibility you can’t get from reading about computational complexity in a textbook — it comes from getting your hands dirty.
From “You Can Use It Without Knowing How It Works” to “You Can Make Judgments Because You Know How It Works”
Even with my long IT infrastructure background, understanding the mechanics behind the sorting operations I’d been using without a second thought was more eye-opening than I expected.
When writing a database ORDER BY clause, you almost never think about which sorting algorithm is running behind the scenes. But when a performance issue arises, having an intuition for sorting complexity — or not — makes a real difference in how quickly you can isolate the cause of “why is this query slow?”
People who understand what’s happening under the hood versus those who don’t approach troubleshooting and performance tuning from fundamentally different vantage points. It’s the shift from “as long as it works” to “I can make informed decisions because I understand the internals.” I didn’t expect that bubble sort — the simplest algorithm of all — would be the catalyst for that shift.
This experience also influenced my communication as a technologist. For instance, when someone reports “this batch process is slow,” there’s a world of difference between saying “it got slower because the data volume increased” and explaining “the algorithm’s processing time grows proportionally to the square of the data volume, so when data doubles, processing time quadruples.” Whether you carry algorithmic fundamentals as an internalized intuition or not changes how precisely you can explain technical problems to non-technical audiences.
Some Understanding Can Only Be Gained by Getting Your Hands Dirty
The strongest conviction I came away with from this assignment is that “understanding through reading” and “understanding through doing” reach entirely different depths of comprehension.
You can understand bubble sort’s mechanics in five minutes by reading a textbook. Compare adjacent elements and swap. That’s all there is to it. But when you draw the flowchart yourself, implement it as a program, wrestle with bugs, and track down the cause through debugging — after going through that entire process, “why a nested loop is necessary,” “why variable initialization placement matters,” and “why a single flag changes efficiency” become things you understand not as theory but as lived experience.
This isn’t limited to technology. In management, someone who only read about a framework in a book and someone who actually applied it on a project and struggled through it have completely different depth of understanding for the same framework. The gap between “understanding” and “being able to do” can only be closed by getting your hands dirty. I think the reason the business school class used a seemingly simple tool like Scratch was precisely to make students experience this gap firsthand.
This Assignment Became the Foundation for What Came Next
Looking back, the bubble sort experience wasn’t just about learning a sort — it built a foundation for “thinking algorithmically” as a way of thought.
Decompose a problem, translate it into steps, and improve efficiency. Define input and output, then design the process between them. Anticipate exceptions and clarify termination conditions — all of these are skills that apply to business problem-solving, not just programming.
In Session 2, I acquired the “building blocks” of lists and loops. In Session 3, I used them to construct an “algorithm.” This sense of cumulative learning served as a running start toward the upcoming phase of “applying algorithms to business challenges.” From pure programming exercises to business problems — this bridging is what makes Technovate Thinking’s curriculum design so masterful, and it’s something I only fully appreciated in hindsight.
Next Up: Designing E-Commerce Recommendations — Applying Algorithms to Business
In the second half of Session 3, the perspective shifts dramatically from programming to business challenges. I’ll write about how I applied the algorithmic thinking from bubble sort in a business context through recommendation system design.


