What I learned while teaching C programming on YouTube

Sharing knowledge with others is often a great way to refresh and update your own expertise.
87 readers like this
87 readers like this
Person reading a book and digital copy

The act of breaking something down in order to teach it to others can be a great way to reacquaint yourself with some old concepts and, in many cases, gain new insights.

I have a YouTube channel where I demonstrate FreeDOS programs and show off classic DOS applications and games. The channel has a small following, so I tend to explore the topics directly suggested by my audience. When several subscribers asked if I could do more videos about programming, I decided to launch a new video series to teach C programming. I learned a lot from teaching C, and in the process, I came across some meaningful takeaways I think others will appreciate.

Make a plan

For my day job, I lead training and workshops to help new and emerging IT leaders develop new skills. Outside of regular work, I also enjoy teaching as an adjunct professor. So I'm very comfortable constructing a course outline and designing a curriculum. That's where I started. If you want to teach a subject effectively, you can't just wing it.

Start by writing an outline of what topics you want to cover and figure out how each new topic will build on the previous ones. The "building block" method of adding new knowledge is key to an effective training program.

To teach C programming as a "follow along" video series, I created this initial outline:

  1. Introduction to C programming—#include, #define, main(), data types, and operators
  2. Flow control—flow control and loops
  3. Functions—user-defined, standard library, and recursion
  4. Arrays—fixed-size arrays, pointers, and variable-sized arrays
  5. Files—reading and writing files
  6. Advanced programming—realloc, getline, and binary
  7. Console programming—conio
  8. Putting it together—writing a turn-based game

Each topic builds upon previous topics, and by the end of the series, we have learned enough about C programming to write a full-screen game.

Show and tell

I originally planned to just record a video series about C programming, but I quickly realized that people would need some kind of written tutorial; there's just too much information to include in a one-hour video. To accompany each week's video, I decided to write a short programming guide to explain the week's topics in more detail. The guide also included lists of new library functions or programming concepts that provided a "quick reference" to learning C.

Fortunately, this worked in my favor. Recording an hour-long video requires planning, and I like to plan. A few days before recording the next video, I wrote out the topics I wanted to cover, and the sample code I wanted to demonstrate on screen. This gave me an outline to narrow the focus of the video. After recording the video, I expanded my notes into a programming guide that I posted online.

Make it immediately applicable

Most people learn best by doing; that's why each "chapter" or "unit" in the series includes several example programs that you can follow to learn about programming. I didn't want the series to be just about the theory of writing programs, but also about actually doing it. For example, in the first chapter, Introduction to C programming, we learn by writing programs to calculate the area of a circle, and how to divide two numbers with a remainder.

Every unit also ends with several "practice programming" tasks that help users to exercise their new knowledge. These exercises directly apply concepts that I introduced in that week's video to reinforce what we learned.

Most importantly, I demonstrate how to write actual FreeDOS programs as part of the video series. For example, in the video where I introduce loops, I also show how to use a do-while loop to write a version of the FreeDOS PAUSE command to wait for the user to press Enter. Throughout the rest of the series, I write versions of FreeDOS ECHO, TYPE, MORE, FIND, CLS, and COPY to demonstrate how to apply new concepts.

Be willing to learn

As I continued in the series, I found it fascinating to explore new topics for myself. For example, because I learned C so long ago, and exercised my C programming by writing programs using C compilers on DOS, I never learned the getline function. This is a newer function that reads a line of arbitrary length from the user. getline is a preferred method to read user input over the fgets function and the more dangerous gets function. But before recording the videos, I didn't know much about getline.

Interestingly, I'd actually written my own versions of getline to use on my own, as I'm sure countless other programmers have. But I didn't realize it was part of the newer C standard, having been added around 2010. In teaching C programming, which by nature requires reading user input, I also learned a "new to me" C programming function.

I also honed my own developer skills. As a self-taught programmer, I know I picked up bad habits early on. Some of those habits were best practices when coding in other programming languages, but aren't great habits in C. AppleSoft BASIC limits variable names to two letters. Fortran can assume variables that start with I-N will be integer variables. So, my default when writing my own programs is to use a simply-named variable like i to iterate through a list, or max to store a maximum value for something.

But in teaching C programming to someone else, I wanted to demonstrate good programming behaviors. I eventually broke my bad habit of short variable names. By the end of the programming video series, I was writing descriptive variable names like colornum to store an index to a list of colors, player to indicate "Player 1" or "Player 2," and message to store a message. I think I've finally broken most of the bad habits of 20+ years of self-taught programming.

Teaching very often goes both ways—as you share knowledge, you pick up new facts and perspectives. No matter your skill or familiarity with a topic, never be afraid to pick up the "teacher" mantle and help someone else learn.

If you want to learn C yourself, you can find the C programming series here.

What to read next
photo of Jim Hall
Jim Hall is an open source software advocate and developer, best known for usability testing in GNOME and as the founder + project coordinator of FreeDOS. At work, Jim is CEO of Hallmentum, an IT executive consulting company that provides hands-on IT Leadership training, workshops, and coaching.

8 Comments

Sir I really enjoyed this article. I agree with it whole-heartedly! Teaching others is very rewarding for many reasons. I also try to do the same thing but with c++ and other similar topics. Keep up the great work!

There is a saying that was used when I was in medical training, about how to learn some procedure you've never done before: "See one, do one, teach one."
The idea was to very briefly explain how to rapidly come to a deep understanding of a procedure or task that's new to you. Even if explained in detail, you don't really know how to do something until you actually do it yourself, and finally, the depth of your understanding must be even greater to be able to explain it to someone else.

I cannot fault your argument but in following through on that with respect to your last example of greater knowledge, I had found that when called upon to explain something to a novice that sometimes, it caused me to realise that I did not have as great an understanding as I first thought. That was of real benefit to me.

In reply to by Greg Pittman

I like i in iterations. Every programmer knows it and it's easier to read inside brackets.

For a short function, I'll still use i. But it has to be something like ten lines long. Otherwise, I prefer to use more descriptive names now, so it's easier to pick up the code later. I aim for 6 to 8 characters long, if I can. Not too long, but long enough that it provides enough description.

And I like to keep names descriptive. These days, if I write a function to evaluate something and return a true/false value, I like to name the function with "is_" as a prefix. For example, the classic "is it odd?" test function is better named as is_odd() rather than just odd(). That way, you have code like this:

if (is_odd(value)) { ... }

In reply to by Cassio Tavares (not verified)

I agree with you guys

Wow -- someone else still remembers AppleSoft? IIRC, though, it allows 238 characters for variable names -- but only the first two are significant, so if you like typing, you can create "more readable" code.

Also, I learned C from the first K&R reference, so many of my iterative loops include i, j, and even k. Yes, this can make it less readable, but it sure saves typing.... I don't even notice myself still doing that today on more complex programs, so thanks for just making me ask myself "Why?"!

Creative Commons LicenseThis work is licensed under a Creative Commons Attribution-Share Alike 4.0 International License.