Functions

Creating a function Revisiting the Payroll Functions to validate Input Summary
Practice Exercise Assignment Part 5

Learning Outcomes

On completion of this section you will be familiar with

Download pdf version

Introduction

Listing 1

1

#C2Interactive Payroll Programme

 2

strName=input("Enter employee's full name:  ")

 3

floatHours=float(input("Enter value for hours:  "))

 4

floatRate=float(input("Enter value for rate:  "))

 5

floatGross=floatHours * floatRate

 6

floatTax=floatGross * 0.25

 7

floatNet=floatGross-floatTax

 8

print("Gross is " + str(floatGross))

 9

print("Tax is " + str(floatTax))

 10

print("Net is " + str(floatNet))

 

Listing 1 above is a reprint of one of the first programmes we wrote.  It is a very simple programme that is very easy to follow since the individual lines of the input, processing and output followed each other in a very logical sequence from top to bottom. There is hardly any need for comments or documentation due to its simplicity. 

Of course this programme was so simple that it was of no use in real life. In order to make it more useful we added an if..else construct in order to calculate the tax. After that we added a if..else..elif construct in order to calculate the superannuation. Finally, in order to validate the hours and rate we added two While loop, one for each value. Recall that the if.. else construct was added to handle the complexity of the tax calculation, the if..elif..else to handle the even more complex superannuation contribution and the while loop to handle the validation of the data going into the variable floatHours. Adding these extra functionalities added to the complexity of the programme and made it difficult to read and interpret.

Our aim here is to restore the original simplicity of the programme.  To do this we shall separate the processing from the main programme so that the main programme will retain the simplicity of Listing 1 above.  The processing we are separating include the calculation of the gross, the tax, the superannuation and the net.  Those are three separate processings which we shall divide up among four separate functions which we shall name calculateGross(), calculateTax(), calculateSuper() and calculateNet(). We shall also create another function that will display the calculated values for the gross, tax, superannuation contribution and the net pay. We shall call this function showData().

As well as making our programme easier to read, functions have another benefit. Suppose that there was a group of lines of programme code that were required to be used in different parts of the programme, we can simply write out the lines of code separately for each part of the programme where they are required. This has two drawbacks:

·         Firstly the more often we retype the lines of code the more likely we are to make a mistake in one of them. This would cause inconsistency in the application.

·         If the routine needs to be altered then we have to make the same alteration wherever the routine occurs. This has the inherent danger that we may miss out one of the instances of the routine.

The other alternative is to write the group of lines together only once and then to call that group whenever we need to use them. This has the following advantages:

How to create a Function

Go to top

Listing 2

 1

def calculateTax(gross):

 2

    if gross<500:

 3

           tax=gross * 0.25

 4

    else:

 5

           tax=125 + (gross-500) * 0.33

 6

    return tax

 

Listing 2 above shows how a function is created.

In line 1 the function is defined using the keyword def.  This is followed by the name of the function – calculateTax, in this case.  The name of the function is followed by and opening and closing bracket and between those you can have as many parameters as you wish.

What is a parameter?  A parameter is a variable that holds a value that has been passed to the function by the main programme, or by another function.  In our case, once our programme has calculated the value of the gross, it calls the function calculateTax() and passes the value of the gross to it.  This value will be stored in the parameter gross.

To finish off the description of the first line of code we must point out the colon at the end of the line.  This colon specifies that lines 2 – 6 are subservient to line 1 or, in other words, are the body of the function.

Lines 2 – 5 consist of an if..else construct.  This construct tests the value of the parameter and if it is less than 500 the value of the local variable tax is calculated in line 3, otherwise the value of tax is calculated at line5.

Line 6 has something new for us – the keyword return. In our case this is followed by the variable tax.  Before describing this keyword we must first look at the concept of local variables.

The variable tax has been created inside the function calculateGross() and is therefore only visible inside the body of the function.  This type of a variable is referred to as a local variable.

Since the variable tax is local to the function calculateGross() it cannot be seen by the main programme and if we need to get the value stored variable back to the main programme we have to use the keyword return to do so.

Once we start examining the main programme we shall show you exactly how this is done.

A revisit to the Payroll

Go to top

Listing 3

 1

#CC8 Functions.py

 2

 

 3

#function for calculating gross

 4

def calculateGross(hours, rate):

 5

    gross=hours*rate

 6

    return gross

 7

 

 8

#function for calculating tax

 9

def calculateTax(gross):

 10

    if gross<500:

 11

           tax=gross * 0.25

 12

    else:

 13

           tax=125 + (gross-500) * 0.33

 14

    return tax

 15

 

 16

#function for calculating superannuation

 17

def calculateSuper(gross,supercode):

 18

    if supercode == 0:

 19

        superAmt = 0

 20

    elif supercode == 1:

 21

        superAmt=gross*0.05

 22

    elif supercode == 2:

 23

        superAmt=gross*0.1

 24

    elif supercode == 3:

 25

        superAmt=gross*0.15

 26

    elif supercode == 4:

 27

        superAmt=gross * 0.2

 28

    else:

 29

        superAmt = -1

 30

    return superAmt

 31

 

 32

#function for calculating the net

 33

def calculateNet(gross, tax, super):

 34

    net=gross - tax - super

 35

    return net

 36

      

 37

#function for displaying results

 38

def showData(gross, tax, super, net):

 39

    print("Gross:    " + str(gross))

 40

    print("Tax:      " + str(tax))

 41

    print("Super:    " + str(super))

 42

    print("Net:      " + str(net))

 43

      

 44

#Main body of programme

 45

 

 46

#input section

 47

strName = input("Enter employee's full name:  ")

 48

floatHours = float(input("Enter value for hours:  "))

 49

floatRate = float(input("Enter value for rate:  "))

 50

intSuperCode = int(input("Enter value for super code:  "))

 51

 

 52

#processing section

 53

floatGross = calculateGross(floatHours, floatRate)

 54

floatTax = calculateTax(floatGross)

 55

floatSuper = calculateSuper(floatGross,  intSuperCode)

 56

floatNet = calculateNet(floatGross,floatTax,floatSuper)

 57

 

 58

#output section

 59

showData(floatGross,floatTax,floatSuper,floatNet)

 

In Listing 3 above lines 1 – 43 is the area where the programme’s functions are stored.  Even though the code for the functions is at the start of the programme the same functions are not executed immediately.  This is because the first line of each function defines it to be a function and Python will not run functions unless they are called from somewhere else.  For this reason we have to get down as far as line 47 before we meet the first line that will be executed.  This line and the three that follow it allow the user to enter values for the employee’s name, the hours worked, the hourly rate and the super code. These lines have not changed since the previous version of the programme and therefore there is no need to discuss them.

The processing section spans lines 53 – 56.  In order to explain it let us assume that the user entered 20, 30 and 2 for the hours, the rate and the super code and that therefore these values are stored in the variables floatHours, floatRate and intSuperCode.

At line 53 the function calculateGross(floatHours, floatRate) is called  This means that control will pass up to line 4 and the values 20 and 30 that were stored in the variables floatHours and floatRate are copied into the parameters hours and rate at line 4.

Once this copying is done, execution of the function begins at line 5.  Here the values of hours and rate, i.e. 20 and 30, are multiplied and the result stored in the local variable gross.  Thus the variable gross has 600 stored in it.

We must get this value back to the main programme. This occurs at line 6 with the code return gross.  This causes programme control to return back to line 53 and to carry the value of the local variable gross with it.  On returning to line 53 the value of gross, i.e. 600 is stored in the variable floatGross.

At line 54 the function calculateTax(floatGross) is called.  This causes programme control to pass to line 9 and also causes the value stored in the variable floatGross, i.e. 600 to be copied to the parameter gross.

Once execution starts the condition at line 10 will be false since 600 is not less than 500 and therefore control will pass to line 13 where tax is calculated as 125 + (600-500) * 0.33 = 125 + 33 = 158.

Line 14 returns this value back to the variable floatTax in line 54.

Once line 54 completes processing, programme control passes to line 55, where the superannuation is calculated.  To calculate the superannuation we need to know the gross pay and the superannuation code.  Therefore the function calculateSuper(floatGross, intSuperCode) is called.  This passes programme control to line 17, where the values 600 and 2 are copied into the parameters gross and supercode.  In the body of the function lines 18 and 20 test the value of supercode for zero and 1 respectively and therefore return a false value.  Line 22, however, tests it for a value of 2.  This, of course, is true and therefore line 23 is executed where the super amount is calculated as 10% of the gross, which in this case is 60. 

Once line 23 has been executed, programme control jumps out of the if..elif..else construct and goes to line 30, where it meets the return statement.  This returns the value of superAmt, i.e. 60, back to line 55 where it is stored in the variable floatSuper.  Once this is complete control passes to line 56.

The value of the net is calculated at line 56.  To do this we simply subtract the tax and superannuation from the gross. To do this the function calculateNet(floatGross, floatTax, floatNet) is called and thus control passes to line 33, where the values 600, 158 and 60 are copied into the parameters gross, tax and super.

At line 34 the value of the  net is calculated as 600 – 158 – 60 = 382, which is then stored in the local variable net.

At lien 35 the keyword return returns the programme control and this value back to line 56 where it is stored in the variable floatNet.

By now the processing is complete and control passes to line 59 which is the first and only line of the output section.  Here the function showData(floatGross, floatTax, floatSuper, floatNet) is called.  Control passes to line 38 where the values 600, 158, 60 and 382 are copied into the variables gross, tax, super and net.  Lines 39 – 42 displays those values along with the appropriate labels.

Notice that there is no return keyword in function showData().  This is because the function does not perform any calculations and that its sole purpose is to present the calculated data to the user. A sample output containing the values discussed here is shown in Figure 1 below.

Figure 1

Before finishing this section let us take a look at the main body of the programme, i.e. lines 46 – 59. We have managed to restore the original simplicity of our original programme:

·         In the input section the requests for data follow each other in logical sequence

·         In the processing section the function names give a clear indication what the functions actually do, making this section self-documenting

Functions for validating Input Data

Go to top

Listing 4

 1

#CC8 Functions.py

 2

 

 3

#function for validating a floating point number

 4

def validateFloat(base, top, prompt):

 5

    floatValue=float(input(prompt))

 6

    while (floatValue<float(base) or floatValue>float(top)):

 7

        print("Value must be in the range "+str(base) + " to " +str(top))

 8

        floatValue=float(input(prompt))

 9

    return floatValue

 10

 

 11

#function for validating an integer

 12

def validateInt(base, top, prompt):

 13

    intValue=int(input(prompt))

 14

    while (intValue<int(base) or intValue>int(top)):

 15

        print("Value must be in the range "+str(base) + " to " +str(top))

 16

        intValue=int(input(prompt))

 17

    return intValue

 

Listing 4 above shows two functions for validating input data.  Both functions are identical in structure and logic.  The only difference between them is that the first one validates floating point numbers while the second one validates integers.  They could be added to the code in Listing 3 so that the hours, hourly rate and superannuation code could be validated as being within allowed ranges.  An example of a call to one of the functions could be:

floatHours = validateFloat(5, 60, “Enter value for hours worked”)

In this case programme control would pass to line 4 of Listing 4 where the values 5, 60 and “Enter values for hours worked” are copied into the parameters base, top and prompt.

Line 5 simply prompts the user to enter a value.  The prompt would appear as follows on the console:

Enter value for hours worked :

This value entered by the user will then be stored in the local variable floatValue.

Line 6, the control line of the while loop tests the new value for being less than the parameter base or greater than the parameter top, or, in our case, being less than 5 or greater than 60.  If either of those conditions is true then the body of the loop is entered.

At line 7 an error message is created by adding together the text item “Values must be in the range , a string version of the parameter base, the text item “ to ” and a string version of the parameter top.  In our case the error message would be:

Value must be in the range 5 to 60

A line 8 the user is again prompted to enter another value and then programme control passes back to line 6.

As with all example, of the while loop this process repeats itself until the user enters a value within the range base to top or 5 – 60 in our case.

Summary

Go to top

Functions are used both to avoid repetition of code within a programme and also in order to make the logic of the programme easier to follow. Data is passed by the calling routine to a function using parameters. The data passed and the arguments must match each other in type. There are two types of functions, those that return a value and those that don’t. The functions must be declared with the keyword def.  This is followed by the name of the function.  This name is followed by a pair of brackets.  Between those brackets are the function’s arguments.  A function may have as many arguments as are necessary.  After a function’s closing brackets you must have a colon to indicate that the following group of indented lines belong to the function’s body.

Practice

Go to top

Copy Listing 3 into a .py file and run it.  Check that it is working satisfactorily.

Once this is running to your satisfaction copy the code in Listing 4 and paste it into the same .py file.  It does not matter where in the .py file you paste this code as long as it is not in the middle of the programme body or in the middle of another function. Now alter the line for inputting the value of hours as follows:

floatHours = validateFloat(5, 60, “Enter value for hours worked”)

Alter the lines for inputting the rate and superannuation code  in the same manner, but remember to call the function validateInt() to validate the super code.

Once the code is running satisfactorily experiment with different lower and upper values for hours rate and super code and check that the altered programme applies those new limits.

Exercise

Go to top
  1. How does the use of functions lead to having better written programmes?
  2. What does an parameters mean as far as functions are concerned?
  3. What co-relation must exist between the parameters and the data passed to them?
  4. Describe in detail the similarities and differences between functions and procedures

Assignment Part 5

Go to top

Modify the code you have created for Assignment Part 4 as follows:

  1. Put the calculation of the subtotal, GST, discount and total into three separate functions called calculateSubtotal, calculateGST, calculateDiscount, calculateTotal.
  2. The function calculateSubtotal will have two arguments, the unit price and the amount sold.
  3. The function calculateGST will have only one argument: the subtotal
  4. The function caculateDiscount will have two arguments: the subtotal and the discount code
  5. The function calculateTotal will have three arguments: the subtotal, the GSt and the discount
  6. There must also be a function for printing the data called showData. This will print out the values of subtotal, GST, discount and total.

Although a major reorganization of the programme has occurred here there has been no change in the actual processing.  The test data for this part will be exactly the same as that for Part 5.