Subroutines

(ToC)

This Video link and the text below it are essentially the same, except the links in the text are hot:
Subroutines (5 minutes) Transcript follows below

Video Transcript: 8. Subroutines

Almost We began this workshop explaining "Five Things You Already Know How To Do," five primitive operations which every computer program that can be written is composed of those Five Things and none others, and that they are all things you already knew how to do. We showed how you use those five things in describing how to make a peanut butter sandwich. Every computer knows how to do those Five Things, and every programming language has a way to tell the computer to do those Five Things, although they are often spelled differently in the different languages, the same as they are spelled (and pronounced) different in different human languages like English and Chinese.

There is one more concept you need to understand as essential to computer programming, and again You Already Know How To Do it, and that is to put a name on a sequence of actions, and then refer to that collection by its name most of the time -- except when you are explaining how to do them.

For example, you programmed the Kitchen Computer to make a "PBJ" and that is the name we called it, and although we did not, we could have told the computer that name, and then when we wanted a PBJ, we'd say "PBJ" and it would make the sandwich. Of course somebody must tell the computer how to make a PBJ (and you already did that), but once that has been done, you can just tell it to do "PBJ" with no further instruction, and it does it.

It's kind of like Iteration, except you don't need to do all the repeats at the same time or in the same part of your program.

The English name for a sequence of steps -- like when a skater does her figures on the ice at the winter Olympics -- is called a "routine" and we sometimes use the same word to describe a sequence of steps in the computer. But most of the time, like

Little fleas have littler fleas
Upon their backs to bite 'em
And littler fleas have littler fleas
And so, ad infinitum.
those routines are calling on other routines, and the programs consist mostly of these littler routines, which we call "subroutines" because they are inside the bigger routines, which are inside... And so, ad infinitum.

You may recall from our RPS game, we started out describing a single play:

1. Synchronization

2. Presenting the plays

3. Deciding the winner

This isn't the whole game, it's just one play. We could make a subroutine out of it:
"OnePlay"
Do Synchronization
Do PresentPlays
Do DecideWinner
Done
where each of our vague descriptions of what is to be done next becomes another subroutine name. The particularization of abstract ideas like this is the essence of "top-down programming." Later on, we can work out the details of exactly what each subroutine does (sometimes called "bottom-up implementation") as for example:
"Synchronization"
Print "One"
Wait 1 second
Print "Two"
Wait 1 second
Print "Three"
Done


In our English programming language you define a subroutine by giving it a name (in quotes) at the top, then ending it with a blank line or the command "Done." And you can do -- usually we say "call" -- it in other parts of the program by spelling out its name on a line by itself, or (better) using the English command "Do".

You might recall that I described three or four different ways to evaluate the score for one play of RPS. Suppose we make each of them a subroutine, and then choose which way we will be scoring the game later on, like in a single line at the top of the program:

Let how = 0  {or -1=Ternary, or +1=Numerical}

"DecideWinner"
if how=0 then do Score6ifs
if how>0 then do Score10h
if how<0 then do ScoreTern
AnnounceWinner
Done


Then finally, the whole game can be understood as just these three lines after the last subroutine has been defined:

Repeat
  OneRPSplay
  Next


When I wrote up the description of how to do ASCII Graphics, I imagined several different ways to do it, so I wrote a subroutine for each different way. That made it easy to test them, and yes, I found several bugs in my code! You will find subroutines useful both for abstraction and for isolating test code. You can use simplistic subroutines in place of difficult algorithms while you get the rest of your program working, then replace the simple subroutine with one that does what you want. And mostly, you can accomplish awesome big software projects incrementally by breaking them into workable chunks (subroutines), then building them one at a time. After it's working, you don't need to waste time looking inside each subroutine all the time.

For more information about subroutines see "Subroutines" in the Kitchen Computer Reference page.
 

Six Things

In summary, Subroutines are the sixth concept in what I call "Six Things" you need to know to program in any language. This list links to where each one is introduced:
1. Sequence -- Commands are (mostly) executed in order

2. Conditional -- You can conditionally skip over some part of the program

3. Input & Output -- The program can be controlled by data not known when it is written,
   and (Output) it can make computed results available for humans or other programs

4. Iteration -- The program can repeat parts of the program multiple times

5. Variables -- The program can remember named pieces of data and change those values during the run

6. Subroutines -- The program can contain named chunks of code, and call on them from various places


A concise summary of all six is in the "Six Things" chapter of "Things You Need to Know in Java" page.
 

Libraries

Libraries are subroutines somebody else wrote. If they are available and do what you need, use them, they save a lot of time writing and debugging code. Really big programs are mostly possible because you can use subroutines that other programmers wrote. It happens two ways, first when programmers work as a team, each person or pair of programmers taking a single subroutine to work on, then everybody else can use it, and then when particularly useful subroutines are collected into a Library that other programmers can use. Pretty much every programming language in wide use has a system library of useful subroutines.
 

OOPS

The proponents of Object-Oriented Programming [Systems] usually argue that "objects" are a totally new and different programming idea, perhaps more important than my "Six Things," but it's not true. Object classes are just subroutines writ large. They are useful for some types of data-centric programs, and not at all helpful -- sometimes even counter-intuitive -- for others. Java is an OOPS language, and when we get there, I will explain how that works. Or you can look ahead and read the "Objects and Classes" chapter of "Things You Need to Know in Java" and/or the section on "OOPS Is Subroutines" in preparation for using the GameEngine.

In OOPS languages like Java, the libraries are all subroutines organized within classes, which define the structure of objects. Often these classes/objects are not a good fit for the subroutines, which makes you work harder to do what you want to do, but that is A Good Thing, because the more time you spend thinking about your problem -- even if it's unnecessary thinking, like overcoming language deficiencies -- means more time looking at what could be bugs (and therefore more opportunities to fix the bugs early, rather than late). Lenient languages like C have been documented to encourage up to "six times more bugs" than tighter languages. You want the language to help you write bug-free code, not make it easier to create brittle code (that breaks easy).
 

[2021 August 31]