Creating New Functions Using Procedural Programming

George E. Hrabovsky

MAST

Introduction

Welcome to lesson two, in this lesson we will begin our discussion of programming in MMA/WL. In this lesson we will describe what we mean by procedural programming. We will then discuss, at great lengths, how we assign symbols to expressions. We will then discuss input and output. We will then get the the heart of procedural programming, how we handle loop-type programming structures. Related to the loops are conditional statements that are directly related to procedural programming. We will end with a discussion of flow control.

It is true that procedural programming is not the most efficient use of MMA/WL. That being true, why address it first? It is mostly due to tradition. The vast majority of programming languages are procedural. It would be foolish to avoid these capabilities. Most people who are familiar with programming are familiar with procedural styles of language. MMA/WL are completely capable of procedural programming. So we begin here.

What is Procedural Programming?

If we have a programming problem and we break it up into smaller tasks that need to be accomplished, each task is composed of a set of specific instructions (an algorithm). Each such task is called a procedure. A procedural program is then built up out of a set of procedures to be performed.

This is an example of a very direct translation of an algorithm into code. Each element of an algorithm has its own procedure. If there are ten elements of an algorithm there will be at least ten elements of the procedural code. One reason why this is the first programming style, or paradigm, learned is that it is so direct. Other paradigms require a more sophisticated view in order to use them, so rather than amping up the learning curve right away, this type of programming is the easiest to understand.

This is all very abstract. How do we make it concrete? We look at an example. What is a good example of a problem we can solve by procedural programming? Say we watch a walnut fall out of a tree and we want to use the computer to tell us how long the nut takes to fall to the ground. How do we set up this problem for procedural programming?

It is an easy problem to solve by hand, if we ignore the air resistance against the fall of the nut. Since we have a computer, let’s use it solve the more difficult problem. Let’s say that we have derived a formula that governs the situation given the initial height above the ground, h. The formula we need to use from the time of fall is,

l2_1.png

Here b is a constant based on the geometry of the nut and the viscosity of the air, we will assume this to be close -1, m is the mass of the nut, we will assume that it is about 0.25 kg, and g is the acceleration due to gravity, about 9.8 l2_2.png. If we insert these values into (2.1) we get,

l2_3.png

All we need to do is input the value of h.

So let's break this down into a set of procedures.

Input the value of h.

Calculate the value of t using (2.2).

Output the value of t.

how do we input the value of h? We will see as we go.

We can use Clear[symbol] to remove all values from a symbol. You can clear a list of symbols in this way.

We can use ClearAll[] to remove all assignments for a symbol.

Input and Output

Input is most often performed by typing into a call. It can also include typing into the arguments slot for a function. We can assign a symbol as input, using the Input command, where the command allows you to treat an expression as input.

l2_4.png

l2_5.png

Note that a dialog box shows up. This is if you are using a notebook front end. If we want to be clearer we can include a prompt.

l2_6.png

l2_7.png

You can also specify a default value.

l2_8.png

l2_9.png

Output is handled automatically as an output cell.

The simplest output command returns whatever expression you tell it to, the Print command.

l2_10.png

l2_11.png

We can style our output using the Style command.

l2_12.png

l2_13.png

Row can be used to produce nicely readable output. It processes a list where each element has its own fixed location in the row.

l2_14.png

l2_15.png

Column works the same way only vertically. Here is a simple example from the documentation.

l2_16.png

1
12
123
1234

Grid is a column of rows.

l2_17.png

a b c
x y z

There are a great many options for creating styled output. You can create your own GUI type programs. As an exercise look up the functions Frame, Background, Alignment, Dividers, and Spacings.

Loops

A loop is an algorithmic construct that repeats in some way until told not to.

This simplest looping structure is the Do loop, where we write Do[expression,the number of iterations]. For example, let’s take the squares of the first ten natural numbers.

l2_18.png

Why didn’t this display anything? Because we didn’t tell it to display anything. We need to tell it to output the result at each step.

l2_19.png

l2_20.png

l2_21.png

l2_22.png

l2_23.png

l2_24.png

l2_25.png

l2_26.png

l2_27.png

l2_28.png

l2_29.png

We can, of course apply all of the iteration commands for MMA/WL. We can specify a minimum and a maximum value

l2_30.png

l2_31.png

l2_32.png

l2_33.png

l2_34.png

l2_35.png

l2_36.png

We can specify a step size.

l2_37.png

l2_38.png

l2_39.png

l2_40.png

l2_41.png

l2_42.png

l2_43.png

l2_44.png

l2_45.png

l2_46.png

l2_47.png

l2_48.png

l2_49.png

l2_50.png

l2_51.png

l2_52.png

l2_53.png

l2_54.png

l2_55.png

l2_56.png

l2_57.png

l2_58.png

We can even specify specific values.

l2_59.png

l2_60.png

l2_61.png

l2_62.png

l2_63.png

Another loop is accomplished using the While command. We will often want to initialize symbols we are going to use. Here we see how to calculate the GCD of two integers.

l2_64.gif

l2_65.png

We can use the Break subcommand to remove us from the While loop to prevent errors. This is an example from the system documentation. Here we use the test InegerQ, the statement !IntegerQ to generate a true result only if the input value is not an integer. So this will only work for positive integers (whole numbers).

l2_66.png

Note that if we input a decimal fraction the program stops due to the Break command.

The For loop begins with an initialization, then it requires a test, then it requires a method of incrementing the value being tested, then  it has the body of the program.

l2_67.png

l2_68.png

l2_69.png

l2_70.png

l2_71.png

l2_72.png

l2_73.png

l2_74.png

l2_75.png

l2_76.png

l2_77.png

Table is a much more useful alternative to these looping structures.

l2_78.png

5. 25.
5.25 27.5625
5.5 30.25
5.75 33.0625
6. 36.
6.25 39.0625
6.5 42.25
6.75 45.5625
7. 49.
7.25 52.5625
7.5 56.25
7.75 60.0625
8. 64.
8.25 68.0625
8.5 72.25
8.75 76.5625
9. 81.
9.25 85.5625
9.5 90.25
9.75 95.0625
10. 100.

Throw and Catch work together. A Throw is a value sent out (thrown) in the form of a value and sometimes a tag. A corresponding Catch has an expression and possibly a form, if the form matches the tag of the the throw. Here we have a value that is not tagged. We define a function with a Throw.

l2_79.png

Now we try some corresponding catches.

l2_80.png

l2_81.png

l2_82.png

l2_83.png

Procedural Conditionals

A conditional is some statement to the effect that if one thing happens, then something else happens.

The most elementary conditional in MMA/WL is the If command. If[conditional statement,is true, is false]. For example, we can define an absolute value command.

l2_84.png

l2_85.png

l2_86.png

We can cheat and use a pattern matching command to make this work on a list. The /@ symbols tells MMA/WL to apply the function to what follows.

l2_87.png

l2_88.png

This illustrates the advantage of using MMA/WL as you can mix programming paradigms seamlessly.

There are a vast number of ways to test expressions. As a homework assignment, you should go to the documentation system and type in Testing Expressions. All of these tests can be used in conditional statements.

The Which command offers a collection of tests and outcomes

l2_89.png

l2_90.png

Flow Control

We can create patterns of flow in the implementation of an algorithm, where we want a specific part of the program to be used.

One way to implement flow control is to use a Module to make a program. We will explore this in more depth in a future lesson. For now we can treat it is device to make self-contained programs. We type Module[{local variables isolated from other work},the list of statements for the modular program;the end result to be displayed].

We can use the Label command to identify places in the program that we want to be able to refer to later.

The Goto command directs the program to go to a specific label. Here is an example drawn from the built-in documentation.

l2_91.png

l2_92.png

l2_93.png

l2_94.png

l2_95.png

Sometimes you want to give the system time for you to respond. You can use the Pause command to stop things for a specified number of seconds.

l2_96.png

l2_97.png

Created with the Wolfram Language