Survey
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
* Your assessment is very important for improving the workof artificial intelligence, which forms the content of this project
Chapter 5 – Functions Up until this point, we have viewed a computer program as a single series of instructions. Most programs, however, consist of distinct groups of instructions, each of which accomplishes a specific task. Such a group of instructions is referred to as a “routine.” Program routines, called “functions” in Python, are a fundamental building block in software development. We take our first look at functions in this chapter. OBJECTIVES After reading this chapter and completing the exercises, you will be able to: Explain the concept of a program routine Explain the concept of parameter passing Explain the concept of value-returning and non-value-returning functions Explain the notion of the side-effects of a function call Differentiate between local scope and global scope Define and use functions in Python Explain the concept of keyword and default arguments in Python Write a Python program using programmer-defined functions Effectively use trace statements for program testing Chapter Overview The purpose of this chapter is to introduce to students the fundamental notion of a program routine (function). This includes function definition, value-returning vs. non-value-returning functions, formal vs. actual arguments, variable scope (local vs. global variables), and the particular Python features of default and keyword arguments. Section 5.1 – Program Routines Section 5.1.1 introduces a routine as a named group of instructions performing some task. A routine is said to be invoked as many times as needed. Routines in Python are said to be called functions. Section 5.1.2 descibes how functions are defined in Python. The terms formal parameters (“parameters”) and actual arguments (“arguments”) are introduced. Also described in this section is the difference between value-returning and non-value-returning functions, with the mention of a side effect resulting from calls to non-value-returning functions. Finally, calls to value-returning functions are described as expressions, and calls to non-value-returning functions as statements. Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 1 Section 5.1.3 Let’s Apply It – “Temperature Conversion Program” (Function Version) This Let’s Apply It section involves the use of both value-returning and non-value-returning functions. The program converts temperatures from Fahrenheit to Celsius and Celsius to Fahrenheit. Section 5.2 – More on Functions In this section, the details of parameter passing in general and in Python is covered. Section 5.2.1 covers the use of value-returning functions, and how the various contexts in which they can be called. An example of tuple assignment, a feature of Python, is mentioned. Section 5.2.2 discusses the use of non-value-returning functions, and the context in which they are called. It is also mentioned here that technically, all functions in Python are value-returning, since when a function value is not explicitly returned by use of the return statement, the special value None is returned. Section 5.2.3 discusses parameter passing in more detail. It is here where mutable vs. immutable arguments in Python are introduced. It is said that it is generally better to define functions that do not return results through the arguments passed, and thus better to return the results through a returned function value. Section 5.2.4 introduces the use of keyword arguments in Python. Here is where the notion of positional arguments is first mentioned. Section 5.2.5 discusses default arguments in Python. Finally, section 5.2.6 discusses variable scope, including local variables (and local scope) and global variables (and global scope). The concept of the lifetime of a variable is also mentioned. It is stated that the use of global variables is generally considered to be bad programming style. Section 5.1.3 Let’s Apply It – “GPA Calculation Program” This Let’s Apply It section involves the use of both value-returning and non-value-returning functions. The program converts temperatures from Fahrenheit to Celsius and Celsius to Fahrenheit. PROGRAM ERATTA The GPA calculation program shown in Figure 5-14 in the text has an error. The getGrades function is missing the last line: return semester_info. This code in the provided source file is correct. Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 2 Section 5.3 COMPUTATIONAL PROBLEM SOLVING – Credit Card Calculation Program This Computational Problem Solving section demonstrates the development of a program that determines the length of time needed to pay off a credit card account for a given balance, interest rate, and monthly payment. It also determines the total interest paid. Section 5.3.1 states the problem as displaying a table (as shown above) that shows the decreasing balance and accumulating interest paid on a credit card account for a given credit card balance, interest rate, and monthly payment. Section 5.3.2 discusses how the minimum payment is typically calculated for a given credit card balance, with the option to make as larger a payment as desired. Section 5.3.3 lays out the program design (and the overall steps of the program). The program requirements are given. The data description points out that only needing numerical values for the loan amount, interest rate, and monthly payment made. The algorithm approach needed is simply the calculation of the requirement minimal payment, which is a percentage of the outstanding balance (2% or 3%), with a lower limit minimum payment (approximately $20). Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 3 Overall Program Steps Section 5.3.4 demonstrates implementation and testing of the program. The program is developed in three stages. Stage 1 develops the initial program, using a top down approach and thus deferring the implementation of the functions called, displayWelcome and displayPayments. These functions are initially implemented to contain only trace statements, that indicated that the functions have been called, and the arguments called with (for function displayPayments). NOTE: There are no intentionally placed errors in the program development. This is the first place in the text in which the notion of a trace statement is discussed. Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 4 SOLUTIONS TO CHAPTER EXERCISES Section 5.1 1. Function avg returns the average of three values, as given in the chapter. Which of the following statements, each making calls to function avg, are valid? (Assume that all variables are of numeric type.) (a) (b) (c) (d) (e) result = avg(n1, n2) result = avg(n1, n2, avg(n3, n4, n5)) result = avg(n1 + n2, n3 + n4, n5 + n6) print(avg(n1, n2, n3)) result = avg(n1, n2, n3) + avg(n4, n5, n6) ANSWER: (b), (c), (d), (e) 2. Which of the following statements, each involving calls to function displayWelcome displaying a welcome message on the screen as given in the chapter, are valid? (a) (b) (c) (d) print(displayWelcome) displayWelcome result = displayWelcome displayWelcome() ANSWER: (d) Section 5.2 3. Suppose there are nine variables, each holding an integer value as shown below, for which the average of the largest value in each line of variables is to be computed. num1 = 10 num4 = 5 num7 = 20 num2 = 20 num5 = 15 num8 = 30 num3 = 25 num6 = 35 num9 = 25 max1 = 25 max2 = 35 max3 = 30 average = (max1 + max2 + max3) / 3.0 = (25 + 35 + 30) / 3.0 = 30.0 Using functions avg and max give an expression that computes the average as shown above using only function calls, and no other operations. ANSWER: avg(max([num1, num2, num3]), max([num4, num5, num6]), max([num7, num8,num9])) Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 5 4. Assume that there exists a Boolean function named isLeapYear that determines if a given year is a leap year or not. Give an appropriate if statement that prints “Year is a Leap Year” if the year passed is a leap year, and “Year is Not a Leap Year” otherwise, for a given variable whichYear. ANSWER: if isLeapYear(whichYear): print('Year is a Leap Year') else: print('Year is Not a Leap Year') 5. For the following function definition and associated function calls, def somefunction(n1, n2): . . # main num1 = 10 somefunction(num1, 15) (a) list all the formal parameters (b) list all the actual arguments ANSWER: (a) n1, n2 (b) num1, 15 6. For the following function, indicate whether each function call is proper or not. If improper, explain why. def gcd(n1, n2): function gcd calculates the greatest common divisor of n1 and n2, with the requirement that n1 be less than or equal to n2, and n1 and n2 are integer values. (a) a = 10 b = 20 result = gcd(a, b) (b) a = 10.0 b = 20 result = gcd(a, b) (c) a = 20 b = 10 result = gcd(b ,a) Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 6 (d) a = 10 b = 20 c = 30 result = gcd(gcd(a, b), c) (e) a = 10 b = 20 c = 30 print gcd(a, gcd(c, b)) ANSWERS: (a) (b) (c) (d) (e) VALID INVALID. Only takes integer arguments. VALID VALID INVALID. First argument must be less than or equal to second argument. Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 7 SOLUTIONS TO PYTHON PROGRAMMING EXERCISES P1. Write a Python function named zeroCheck that is given three integers, and returns true if any of the integers is 0, otherwise it returns false. def zeroCheck(n1, n2, n3): if n1 * n2 * n3 == 0: return True else: return False P2. Write a Python function named ordered3 that is passed three integers, and returns true if the three integers are in order from smallest to largest, otherwise it returns false. def ordered3(n1, n2, n3): if n1 < n2 and n2 < n3: return True else: return False P3. Write a Python function named modCount that is given a positive integer, n, and a second positive integer, m <= n, and returns how many numbers between 1 and n are evenly divisible by m. def modCount(n, m): count = 0 for k in range(2, n): if k % m == 0: count = count + 1 return count P4. Write a Python function named helloWorld that displays "Hello World, my name is name ", for any given name passed to the routine. def helloWorld(name): print('Hello world, my name is', name) P5. Write a Python function named printAsterisks that is passed a positive integer value n, and prints out a line of n asterisks. If n is greater than 75, then only 75 asterisks should be displayed. def printAsterisks(n): if n > 75: n = 75; for k in range(0, n + 1): print('*', end='') print() Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 8 P6. Write a Python function named getContinue that displays to the user “Do you want to continue (y/n): ”, and continues to prompt the user until either uppercase or lowercase 'y' or 'n' is entered, returning (lowercase) 'y' or 'n' as the function value. def getContinue(): response = input('Do you want to continue (y:n): ') while response not in ('y', 'n', 'Y', 'N'): response = input('Do you want to continue (y:n): ') if response in ('y', 'Y'): return 'y' else: return 'n' NOTE: This solution assumes that string methods upper/lower have not yet been covered (introduced in Chapter 8 on Text Files). P7. Implement a Python function that is passed a list of numeric values and a particular threshold value, and returns the list with all values above the given threshold value set to 0. The list should be altered as a side effect to the function call, and not by function return value. def filterValues(lst, threshold_val): for k in range(0, len(lst)): if lst[k] > threshold_val: lst[k] = 0 P8. Implement the Python function described in question P7 so that the altered list is returned as a function value, rather than by side effect. def filterValues(lst, threshold_val): new_list = [] for k in range(0, len(lst)): if lst[k] > threshold_val: new_list.append(0) else: new_list.append(lst[k]) return new_list Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 9 SOLUTIONS TO PROGRAM MODIFICATION PROBLEMS M1. Temperature Conversion Program: Adding Kelvin Scale Modify the Temperature Conversion program in section 5.1.3 so that it allows the user to select temperature conversion to include degrees Kelvin, in addition to degrees Fahrenheit and degrees Celsius. Include input error checking for inappropriate temperature values. (NOTE: Refer to questions M1 and M2 from Chapter 3.) # Temperature Conversion Program (Figure 5-6) # MODIFICATION: Allow conversion between Kelvin scale def displayWelcome(): print('This program will convert a range of temperatures between') print('Fahrenheit, Celsius and Kelvin\n') def getScale(): which = input('Enter (F)ahrenheit, (C)elsius, or (Kelvin): ') while which not in ('F', 'C', 'K'): which = input('Enter (F)ahrenheit, (C)elsius, or (K)elvin: ') return which def displayConversion(from_scale, to_scale, start, end): scales = ('F', 'C', 'K') scale_names = ('Fahrenheit', 'Celsius', 'Kelvin') print() print(format('Degrees', '^12'), format('Degrees', '^12')) print(format(scale_names[scales.index(from_scale)], '^12'), format(scale_names[scales.index(to_scale)], '^12')) for temp in range(start, end + 1): if from_scale == 'F': if to_scale == 'C': converted_temp = (temp - 32) * 5/9 if to_scale == 'K': converted_temp = ((temp - 32) * 5/9) + 273.15 elif from_scale == 'C': if to_scale == 'F': converted_temp = (9/5 * temp) + 32 elif to_scale == 'K': converted_temp = temp + 273.15 elif from_scale == 'K': if to_scale == 'F': converted_temp = (9/5 * (temp - 273.13)) + 32 elif to_scale == 'C': converted_temp = temp - 273.15 print(format(temp, '8.1f'), format(' ', '^3'), format(converted_temp, '8.1f')) Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 10 # ---- main # Display program welcome displayWelcome() # Get temperature scales to convert between print('Enter temperature scale to convert from ...') convert_from = getScale() print('\nEnter temperature scale to convert to ...') convert_to = getScale() # Get range of temperatures to convert valid_temp = False while not valid_temp: temp_start = int(input('\nEnter start of temperature range to convert: ')) if (convert_from == 'F' and temp_start >= -459) or \ (convert_from == 'C' and temp_start >= -273) or \ (convert_from == 'K' and temp_start >= 0): valid_temp = True else: print('Temperature entered below absolute zero') temp_end = int(input('Enter ending temperature to convert: ')) while temp_end < temp_start: print('End temperature cannot be less than starting temperature') temp_end = int(input('Enter ending temperature to convert: ')) # Display range of converted temperatures displayConversion(convert_from, convert_to, temp_start, temp_end) This program will convert a range of temperatures between Fahrenheit, Celsius and Kelvin Enter temperature scale to convert from ... Enter (F)ahrenheit, (C)elsius, or (Kelvin): F Enter temperature scale to convert to ... Enter (F)ahrenheit, (C)elsius, or (K)elvin: C Enter start of temperature range to convert: 75 Enter ending temperature to convert: 90 Degrees Fahrenheit 75.0 76.0 77.0 78.0 79.0 80.0 81.0 82.0 83.0 84.0 85.0 86.0 87.0 88.0 89.0 90.0 Degrees Celsius 23.9 24.4 25.0 25.6 26.1 26.7 27.2 27.8 28.3 28.9 29.4 30.0 30.6 31.1 31.7 32.2 Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 11 This program will convert a range of temperatures between Fahrenheit, Celsius and Kelvin Enter temperature scale to convert from ... Enter (F)ahrenheit, (C)elsius, or (Kelvin): F Enter temperature scale to convert to ... Enter (F)ahrenheit, (C)elsius, or (Kelvin): K Enter start of temperature range to convert: 75 Enter ending temperature to convert: 90 Degrees Fahrenheit 75.0 76.0 77.0 78.0 79.0 80.0 81.0 82.0 83.0 84.0 85.0 86.0 87.0 88.0 89.0 90.0 Degrees Kelvin 297.0 297.6 298.1 298.7 299.3 299.8 300.4 300.9 301.5 302.0 302.6 303.1 303.7 304.3 304.8 305.4 This program will convert a range of temperatures between Fahrenheit, Celsius and Kelvin Enter temperature scale to convert from ... Enter (F)ahrenheit, (C)elsius, or (Kelvin): K Enter temperature scale to convert to ... Enter (F)ahrenheit, (C)elsius, or (Kelvin): C Enter start of temperature range to convert: -100 Temperature entered below absolute zero Enter start of temperature range to convert: 0 Enter ending temperature to convert: 10 Degrees Kelvin 0.0 1.0 2.0 3.0 4.0 5.0 6.0 7.0 8.0 9.0 10.0 Degrees Celsius -273.1 -272.1 -271.1 -270.1 -269.1 -268.1 -267.1 -266.1 -265.1 -264.1 -263.1 Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 12 M2. GPA Calculation Program: Accommodating First-Semester Students Modify the GPA Calculation Program of section 5.2.7 so that it asks the student if this is their first semester of grades. If so, the program should only prompt the students for their current semester grades, and not their cumulative gpa and total earned credits, and display their semester gpa and cumulative gpa accordingly. # Temperature GPA Calculation Program (Figure 5-13) # MODIFICATION: Accommodating First-Semester Students def convertGrade(grade): if grade == 'F': return 0 else: return 4 - (ord(grade) - ord('A')) def getGrades(): semester_info = [] more_grades = True empty_str = '' print("Enter current semester grades ('A','B','C','D','F')") while more_grades: course_grade = input('Enter grade (hit Enter when done): ') while course_grade not in ('A','B','C','D','F',empty_str): course_grade = input('Enter letter grade received: ') if course_grade == empty_str: more_grades = False else: num_credits = int(input('Enter number of credits: ')) semester_info.append([num_credits, course_grade]) return semester_info def calculateGPA(sem_grades_info, cumulative_gpa_info): sem_quality_pts = 0 sem_credits = 0 current_cumulative_gpa, total_credits = cumulative_gpa_info for k in range(len(sem_grades_info)): num_credits, letter_grade = sem_grades_info[k] sem_quality_pts = sem_quality_pts + \ num_credits * convertGrade(letter_grade) sem_credits = sem_credits + num_credits sem_gpa = sem_quality_pts / sem_credits new_cumulative_gpa = (current_cumulative_gpa * total_credits +\ sem_gpa * sem_credits) / (total_credits + sem_credits) return (sem_gpa, new_cumulative_gpa) Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 13 # ---- main # program greeting print('This program calculates semester and cumulative GPAs\n') # first semester student? response = input('Is this your first semester (y/n)? ') while response not in ('y', 'n', 'Y', 'N'): response = input('Is this your first semester (y/n)? ') first_semester = response in ('Y', 'y') # get current semester grade info print() semester_grades = getGrades() if first_semester: cumulative_gpa_info = (0, 0) else: total_credits = int(input('\nEnter total number of earned credits: ')) cumulative_gpa = float(input('Enter your current cumulative GPA: ')) cumulative_gpa_info = (cumulative_gpa, total_credits) # calculate semester gpa and new cumulative gpa semester_gpa, cumulative_gpa = calculateGPA(semester_grades, \ cumulative_gpa_info) # display semester gpa and new cumulative gpa print('\nYour semester GPA is', format(semester_gpa, '.2f')) print('Your new cumulative GPA is', format(cumulative_gpa, '.2f')) This program calculates semester and cumulative GPAs Is this your first semester (y/n)? y Enter Enter Enter Enter Enter Enter Enter Enter Enter Enter current semester grades ('A','B','C','D','F') grade (hit Enter when done): A number of credits: 3 grade (hit Enter when done): B number of credits: 3 grade (hit Enter when done): B number of credits: 3 grade (hit Enter when done): A number of credits: 3 grade (hit Enter when done): Your semester GPA is 3.50 Your new cumulative GPA is 3.50 Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 14 This program calculates semester and cumulative GPAs Is this your first semester (y/n)? n Enter Enter Enter Enter Enter Enter Enter Enter Enter Enter current semester grades ('A','B','C','D','F') grade (hit Enter when done): A number of credits: 3 grade (hit Enter when done): B number of credits: 3 grade (hit Enter when done): B number of credits: 3 grade (hit Enter when done): A number of credits: 3 grade (hit Enter when done): Enter total number of earned credits: 12 Enter your current cumulative GPA: 3.2 Your semester GPA is 3.50 Your new cumulative GPA is 3.35 M3. GPA Calculation Program: Allowing for Plus/Minus Grading Modify the GPA Calculation Program of section 5.2.7 so that it is capable of calculating a GPA for plus/minus letter grades: A, A-, B+, B, B-, and so forth. # GPA Calculation Program (Figure 5-14) # MODIFICATION: Allowing for Plus/Minus Grading def convertGrade(grade): adjustment = 0.33 # get base grade if grade[0] == 'F': value = 0 else: value = 4 - (ord(grade[0]) - ord('A')) # make adjustment for any +/if len(grade) == 2: if grade[1] == '+': value = value + adjustment else: value = value - adjustment return value def getGrades(valid_grades): semester_info = [] more_grades = True empty_str = '' print("Enter current semester grades ('A','A-','B+', ...)") while more_grades: Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 15 course_grade = input('Enter grade (hit Enter if done): ') if course_grade == empty_str: more_grades = False elif len(course_grade) == 1 or len(course_grade) == 2 and \ course_grade in valid_grades: num_credits = int(input('Enter number of credits: ')) print() semester_info.append([num_credits, course_grade]) else: print('Invalid Grade -- Reenter: ') return semester_info def calculateGPA(sem_grades_info, cumulative_gpa_info): sem_quality_pts = 0 sem_credits = 0 current_cumulative_gpa, total_credits = cumulative_gpa_info for k in range(len(sem_grades_info)): num_credits, letter_grade = sem_grades_info[k] sem_quality_pts = sem_quality_pts + \ num_credits * convertGrade(letter_grade) sem_credits = sem_credits + num_credits sem_gpa = sem_quality_pts / sem_credits new_cumulative_gpa = (current_cumulative_gpa * total_credits +\ sem_gpa * sem_credits) / (total_credits + sem_credits) return (sem_gpa, new_cumulative_gpa) # ---- main # init valid_grades = ('A','A-','B+','B','B-','C+','C','C-','D+','D','D-','F') # program greeting print('This program calculates semester and cumulative GPAs\n') # get current GPA info total_credits = int(input('Enter total number of earned credits: ')) cumulative_gpa = float(input('Enter your current cumulative GPA: ')) cumulative_gpa_info = (cumulative_gpa, total_credits) # get current semester grade info print() semester_grades = getGrades(valid_grades) # calculate semester gpa and new cumulative gpa semester_gpa, cumulative_gpa = calculateGPA(semester_grades, \ cumulative_gpa_info) # display semester gpa and new cumulative gpa print('\nYour semester GPA is', format(semester_gpa, '.2f')) print('Your new cumulative GPA is', format(cumulative_gpa, '.2f')) Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 16 This program calculates semester and cumulative GPAs Enter total number of earned credits: 30 Enter your current cumulative GPA: 3.4 Enter current semester grades ('A','A-','B+', ...) Enter grade (hit Enter if done): AEnter number of credits: 3 Enter grade (hit Enter if done): B++ Invalid Grade -- Reenter: Enter grade (hit Enter if done): B+ Enter number of credits: 3 Enter grade (hit Enter if done): BEnter number of credits: 4 Enter grade (hit Enter if done): A Enter number of credits: 3 Enter grade (hit Enter if done): C+ Enter number of credits: 2 Enter grade (hit Enter if done): Your semester GPA is 3.22 Your new cumulative GPA is 3.34 M4. Credit Card Calculation Program: Summarized Output Modify the Credit Card Calculation Program in section 5.3.3 so that the user is given the option of either displaying the balance and interest paid month-by-month as currently written, or to simply have the total number of months and the total interest paid without the month-by-month detail. # Credit Card Calculation Program (Section 5.3) # MODIFICATION: Summarized Output def displayWelcome(): print('This program will determine the time to pay off a credit') print('card and the interest paid based on the current balance,') print('the interest rate, and the monthly payments made.') def displayPayments(balance, int_rate, monthly_payment): # init num_months = 0 total_int_paid = 0 num_payments = 1 empty_year_field = format(' ', '8') Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 17 # display heading print('\n', format('PAYOFF SCHEDULE','>20')) print(format('Year','>10') + format('Balance','>10') + format('Payment Num', '>14') + format('Interest Paid','>16')) # display year-by-year account status while balance > 0: monthly_int = balance * int_rate total_int_paid = total_int_paid + monthly_int balance = balance + monthly_int - monthly_payment if balance < 0: balance = 0 if num_months % 12 == 0: year_field = format(num_months // 12 + 1, '>8') else: year_field = empty_year_field print(year_field + format(balance, '>12,.2f') + format(num_payments, '>9') + format(total_int_paid, '>17,.2f')) num_payments = num_payments + 1 num_months = num_months + 1 def displayBottomLine(balance, int_rate, monthly_payment): # init num_months = 0 total_int_paid = 0 num_payments = 0 # calculate number of payments and total interest paid while balance > 0: monthly_int = balance * int_rate total_int_paid = total_int_paid + monthly_int balance = balance + monthly_int - monthly_payment num_payments = num_payments + 1 # display heading print('\nTOTAL NUMBER OF PAYMENTS:', num_payments, format(' ', '4<'), 'TOTAL INTEREST PAID: ', format(total_int_paid, ',.2f')) # ---- main # display welcome screen displayWelcome() # get current balance and APR balance = int(input('\nEnter the balance on your credit card: ')) apr = int(input('Enter the interest rate (APR) on the card: ')) monthly_int_rate = apr/1200 yes_response = ('y','Y') no_response = ('n','N') Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 18 calc = True while calc: # calc minimum monthly payment if balance < 1000: min_monthly_payment = 20 else: min_monthly_payment = balance * .02 # get monthly payment print('\nAssuming a minimum payment of 2% of the balance ($20 min)') print('Your minimum payment would be', format(min_monthly_payment, '.2f'),'\n') response = input('Use the minimum monthly payment? (y/n): ') while response not in yes_response + no_response: response = input('Use the minimum monthly payment? (y/n): ') if response in yes_response: monthly_payment = min_monthly_payment else: acceptable_payment = False while not acceptable_payment: monthly_payment = int(input('\nEnter monthly payment: ')) if monthly_payment < balance * .02: print('Minimum payment of 2% of balance required ($' + str(balance * .02) + ')') elif monthly_payment < 20: print('Minimum payment of $20 required') else: acceptable_payment = True # check if single payment pays off balance if monthly_payment >= balance: print('* This payment amount would pay off your balance *') else: # display number of payments and interest paid prompt = 'Do you wish to see the monthy payment details (y/n)? ' monthly_output = input(prompt) while monthly_output not in ('Y','N','y','n'): monthly_output = input(prompt) if monthly_output in ('Y','y'): displayPayments(balance, monthly_int_rate, monthly_payment) else: displayBottomLine(balance, monthly_int_rate, monthly_payment) # calculate again with another monthly payment? again = input('\nRecalculate with another payment? (y/n): ') while again not in yes_response + no_response: again = input('Recalculate with another payment? (y/n): ') if again in yes_response: calc = True # continue program print('\n\nFor your current balance of $' + str(balance)) else: calc = False # terminate program Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 19 This program will determine the time to pay off a credit card and the interest paid based on the current balance, the interest rate, and the monthly payments made. Enter the balance on your credit card: 2500 Enter the interest rate (APR) on the card: 18 Assuming a minimum payment of 2% of the balance ($20 min) Your minimum payment would be 50.00 Use the minimum monthly payment? (y/n): n Enter monthly payment: 125 Do you wish to see the monthy payment details (y/n)? n TOTAL NUMBER OF PAYMENTS: 24 TOTAL INTEREST PAID: 494.57 Recalculate with another payment? (y/n): y For your current balance of $2500 Assuming a minimum payment of 2% of the balance ($20 min) Your minimum payment would be 50.00 Use the minimum monthly payment? (y/n): n Enter monthly payment: 250 Do you wish to see the monthy payment details (y/n)? y PAYOFF SCHEDULE Year Balance 1 2,287.50 2,071.81 1,852.89 1,630.68 1,405.14 1,176.22 943.86 708.02 468.64 225.67 0.00 Payment Num 1 2 3 4 5 6 7 8 9 10 11 Interest Paid 37.50 71.81 102.89 130.68 155.14 176.22 193.86 208.02 218.64 225.67 229.06 Recalculate with another payment? (y/n): n >>> Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 20 M5. Credit Card Calculation Program: Adjustable Minimum Payment Modify the Credit Card Calculation program in section 5.3 so that the user can enter the percentage from which the minimum monthly payment is calculated. Also modify the program so that this minimum payment percentage is displayed along with the other credit card related information. # Credit Card Calculation Program (Section 5.3) # MODIFICATION: Adjustable Minimum Payment def displayWelcome(): print('This program will determine the time to pay off a credit') print('card and the interest paid based on the current balance,') print('the interest rate, and the monthly payments made.') def displayPayments(balance, int_rate, monthly_payment): # init num_months = 0 total_int_paid = 0 payment_num = 1 empty_year_field = format(' ', '8') # display heading print('\n', format('PAYOFF SCHEDULE','>20')) print(format('Year','>10') + format('Balance','>10') + format('Payment Num', '>14') + format('Interest Paid','>16')) # display year-by-year account status while balance > 0: monthly_int = balance * int_rate total_int_paid = total_int_paid + monthly_int balance = balance + monthly_int - monthly_payment if balance < 0: balance = 0 if num_months % 12 == 0: year_field = format(num_months // 12 + 1, '>8') else: year_field = empty_year_field print(year_field + format(balance, '>12,.2f') + format(payment_num, '>9') + format(total_int_paid, '>17,.2f')) payment_num = payment_num + 1 num_months = num_months + 1 # ---- main # init yes_response = ('y','Y') no_response = ('n','N') (moved here) # display welcome screen displayWelcome() Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 21 # get current balance and APR balance = int(input('\nEnter the balance on your credit card: ')) apr = int(input('Enter the interest rate (APR) on the card: ')) monthly_int_rate = apr/1200 # get percentage for minimum monthly payment percent_min = int(input('Enter percentage used to calculate min payment: ')) while percent_min < 1: percent_min = input('Enter as integer value (e.g., 18): ') # calc minimum monthly payment min_monthly_payment = balance * (percent_min / 100) if min_monthly_payment < 20: min_monthly_payment = 20 # display payments and interest paid calc = True while calc: # get monthly payment print('\nAssuming a minimum payment of',str(percent_min) + '% of the balance, \nyour minimum payment would be', format(min_monthly_payment, '.2f'),'\n') response = input('Use the minimum monthly payment? (y/n): ') while response not in yes_response + no_response: response = input('Use the minimum monthly payment? (y/n): ') if response in yes_response: monthly_payment = min_monthly_payment else: acceptable_payment = False while not acceptable_payment: monthly_payment = int(input('\nEnter monthly payment: ')) if monthly_payment < balance * (percent_min / 100): print('Minimum payment of', str(percent_min) + '% of the balance required ($' + str(balance * (percent_min / 100)) + ')') elif monthly_payment < 20: print('Minimum payment of $20 required') else: acceptable_payment = True # check if single payment pays off balance if monthly_payment >= balance: print('* This payment amount would pay off your balance *') else: # display month-by-month balance payoff displayPayments(balance, monthly_int_rate, monthly_payment) # calculate again with another monthly payment? again = input('\nRecalculate with another payment? (y/n): ') while again not in yes_response + no_response: again = input('Recalculate with another payment? (y/n): ') if again in yes_response: calc = True # continue program print('\n\nFor your current balance of $' + str(balance)) else: calc = False # terminate program Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 22 This program will determine the time to pay off a credit card and the interest paid based on the current balance, the interest rate, and the monthly payments made. Enter the balance on your credit card: 2500 Enter the interest rate (APR) on the card: 18 Enter percentage used to calculate min payment: 3 Assuming a minimum payment of 3% of the balance, your minimum payment would be 75.00 Use the minimum monthly payment? (y/n): n Enter monthly payment: 60 Minimum payment of 3% of balance required ($75.0) Enter monthly payment: 100 PAYOFF SCHEDULE Year Balance 1 2,437.50 2,374.06 2,309.67 2,244.32 2,177.98 2,110.65 2,042.31 1,972.95 1,902.54 1,831.08 1,758.55 1,684.92 2 1,610.20 1,534.35 1,457.37 1,379.23 1,299.92 1,219.41 1,137.71 1,054.77 970.59 885.15 798.43 710.40 3 621.06 530.38 438.33 344.91 250.08 153.83 56.14 0.00 Payment Num 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 Interest Paid 37.50 74.06 109.67 144.32 177.98 210.65 242.31 272.95 302.54 331.08 358.55 384.92 410.20 434.35 457.37 479.23 499.92 519.41 537.71 554.77 570.59 585.15 598.43 610.40 621.06 630.38 638.33 644.91 650.08 653.83 656.14 656.98 Recalculate with another payment? (y/n): n >>> Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 23 M6. Credit Card Calculation Program: Recalculation with New Balance Modify the Credit Card Calculation program in section 5.3 so that the program will allow the user to recalculate a new payoff schedule for a new entered balance. # Credit Card Calculation Program (Section 5.3) # MODIFICATION: Recalculation with New Balance def displayWelcome(): print('This program will determine the time to pay off a credit') print('card and the interest paid based on the current balance,') print('the interest rate, and the monthly payments made.') def displayPayments(balance, int_rate, monthly_payment): # init num_months = 0 total_int_paid = 0 payment_num = 1 empty_year_field = format(' ', '8') # display heading print('\n', format('PAYOFF SCHEDULE','>20')) print(format('Year','>10') + format('Balance','>10') + format('Payment Num', '>14') + format('Interest Paid','>16')) # display year-by-year account status while balance > 0: monthly_int = balance * int_rate total_int_paid = total_int_paid + monthly_int balance = balance + monthly_int - monthly_payment if balance < 0: balance = 0 if num_months % 12 == 0: year_field = format(num_months // 12 + 1, '>8') else: year_field = empty_year_field print(year_field + format(balance, '>12,.2f') + format(payment_num, '>9') + format(total_int_paid, '>17,.2f')) payment_num = payment_num + 1 num_months = num_months + 1 # ---- main # display welcome screen displayWelcome() # get current balance and APR balance = int(input('\nEnter the balance on your credit card: ')) apr = int(input('Enter the interest rate (APR) on the card: ')) monthly_int_rate = apr/1200 yes_response = ('y','Y') no_response = ('n','N') calc = True Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 24 while calc: # calc minimum monthly payment if balance < 1000: min_monthly_payment = 20 else: min_monthly_payment = balance * .02 # get monthly payment print('\nAssuming a minimum payment of 2% of the balance ($20 min)') print('Your minimum payment would be', format(min_monthly_payment, '.2f'),'\n') response = input('Use the minimum monthly payment? (y/n): ') while response not in yes_response + no_response: response = input('Use the minimum monthly payment? (y/n): ') if response in yes_response: monthly_payment = min_monthly_payment else: acceptable_payment = False while not acceptable_payment: monthly_payment = int(input('\nEnter monthly payment: ')) if monthly_payment < balance * .02: print('Minimum payment of 2% of balance required ($' + str(balance * .02) + ')') elif monthly_payment < 20: print('Minimum payment of $20 required') else: acceptable_payment = True # check if single payment pays off balance if monthly_payment >= balance: print('* This payment amount would pay off your balance *') else: # display month-by-month balance payoff displayPayments(balance, monthly_int_rate, monthly_payment) # calculate again? response = input('\nDo you wish to do another calculation? (y/n): ') while response not in yes_response + no_response: response = input('Do you wish to do another calculation? (y/n): ') if response in no_response: calc = False else: response = input('\nRecalculate for another balance? (y/n): ') while response not in yes_response + no_response: again = input('Recalculate for another balance? (y/n): ') if response in yes_response: balance = int(input('\nEnter another balance: ')) Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 25 This program will determine the time to pay off a credit card and the interest paid based on the current balance, the interest rate, and the monthly payments made. Enter the balance on your credit card: 800 Enter the interest rate (APR) on the card: 12 Assuming a minimum payment of 2% of the balance ($20 min) Your minimum payment would be 20.00 Use the minimum monthly payment? (y/n): n Enter monthly payment: 75 PAYOFF SCHEDULE Year Balance 1 733.00 665.33 596.98 527.95 458.23 387.81 316.69 244.86 172.31 99.03 25.02 0.00 Payment Num 1 2 3 4 5 6 7 8 9 10 11 12 Interest Paid 8.00 15.33 21.98 27.95 33.23 37.81 41.69 44.86 47.31 49.03 50.02 50.27 Do you wish to do another calculation? (y/n): y Recalculate for another balance? (y/n): y Enter another balance: 500 Assuming a minimum payment of 2% of the balance ($20 min) Your minimum payment would be 20.00 Use the minimum monthly payment? (y/n): n Enter monthly payment: 75 PAYOFF SCHEDULE Year Balance 1 430.00 359.30 287.89 215.77 142.93 69.36 0.00 Payment Num 1 2 3 4 5 6 7 Interest Paid 5.00 9.30 12.89 15.77 17.93 19.36 20.05 Do you wish to do another calculation? (y/n): n >>> Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 26 SOLUTIONS TO PROGRAM DEVELOPMENT PROBLEMS D1. Metric Conversion Program Develop and test a Python program that allows the user to convert between the metric measurements of millimeter, centimeter, meter, kilometer, and inches, feet, yards, and miles. The program should be written so that any one measurement can be converted to the other. # Metric Conversion Program # Problem D1 (Chapter 5) # This program will convert between the metric measurements of millimeters, # centimeters, meters, kilometers and English units of inches, feet, yards, # and miles. def displayWelcome(): print('This program will convert between metric and English units', 'of linear measure.') print('\nMeasurements entered as <number><space><units>, where', '<units> one of:') print('METRIC UNITS: ', end='') print('mm (millimters), cm (centimeters), m (meters), km (kilometers)') print('\nENGLISH UNITS: ', end='') print('ins (inches), ft (feet), yds (yards), mi (miles)') def getMeasurement(): valid_input = False while not valid_input: measurement = input('\nEnter measurement: ') # check if blank included (and not first/last character entered) if not blank_char in measurement or \ measurement.index(blank_char) == 0 or \ measurement.index(blank_char) == len(measurement) - 1: print('Must be of form <number><space><units>') else: # parse numeric and units info numeric = measurement[0:measurement.index(blank_char)] units = measurement[measurement.index(blank_char) + 1:] # check that numeric part contains only digits and decimal point invalidated_numeric = False k = 0 while not invalidated_numeric and k < len(numeric): if numeric[k] not in digit_chars + ('.',): print('Invalid numeric value found') print('Must be of form <number><space><units>') invalidated_numeric = True else: k = k + 1 # check that units one of mm, cm, m, km, in, ft, yrds, mi if not invalidated_numeric: Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 27 invalidated_units = False if units not in available_units: print('Invalid units found') print('Must be of form <number><space><units>,') print('for units one of mm, cm, m, km, in, ft, yds, mi') invalidated_units = True if not invalidated_numeric and not invalidated_units: valid_input = True return (int(numeric), units) def displayConversion(current_measure, current_units, new_units, units_info): units = units_info[0] conversions = units_info[1] current_conv_factor = conversions[units.index(current_units)] new_conv_factor = conversions[units.index(new_units)] new_measure = (current_conv_factor * current_measure) / new_conv_factor print(current_measure, current_units, '=', format(new_measure, '.2f'), new_units) # ---- main # init blank_char = ' ' digit_chars = ('0', '1', '2', '3', '4', '5', '6', '7', '8', '9') available_units = ('mm', 'cm', 'm', 'km', 'in', 'ft', 'yds', 'mi') conversions = (1, 10, 1000, 1e6, 25.4, 304.8, 914.4, 1.609344e6) # display program welcome displayWelcome() # execute conversions quit = False while not quit: # get measurement measurement, units = getMeasurement() # get units to convert to units_conversion = input('Enter units to convert to: ') while units_conversion not in available_units: print('Invalid units entered - Please reenter') units_conversion = input('Enter units to convert to: ') # display conversion displayConversion(measurement, units, units_conversion, (available_units, conversions)) # continue? response = input('\nDo you wish to do another conversion? (y/n) ') while response not in ('Y', 'N', 'y', 'n'): response = input('Do you wish to do another conversion? (y/n) ') if response in ('N', 'n'): quit = True Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 28 This program will convert between metric and English units of linear measure. Measurements entered as <number><space><units>, where <units> one of: METRIC UNITS: mm (millimters), cm (centimeters), m (meters), km (kilometers) ENGLISH UNITS: ins (inches), ft (feet), yds (yards), mi (miles) Enter measurement: 1 cm Enter units to convert to: mm 1 cm = 10.000000 mm Do you wish to do another conversion? (y/n) y Enter measurement: 1 in Enter units to convert to: cm 1 in = 2.540000 cm Do you wish to do another conversion? (y/n) y Enter measurement: 1 mi Enter units to convert to: ft 1 mi = 5280.000000 ft Do you wish to do another conversion? (y/n) y Enter measurement: 1 mm Enter units to convert to: mi 1 mm = 0.000001 mi Do you wish to do another conversion? (y/n) y Enter measurement: 1 km Enter units to convert to: mi 1 km = 0.621371 mi Do you wish to do another conversion? (y/n) n >>> Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 29 D2. GPA Projection Program Develop and test a Python program that lets the user enter their current cumulative GPA, their total credits earned, and the number of credits they are currently taking. The program should then request from the user a target cumulative GPA that they wish to achieve, and display the GPA of the current semester needed to achieve it. # Problem D2 (Chapter 5) # This program will allow a student to determine what GPA is needed for the # current semester to attain a specific cumulative GPA. def convertGrade(grade): if grade == 'F': return 0 else: return 4 - (ord(grade) - ord('A')) def getGrades(): semester_info = [] more_grades = True empty_str = '' while more_grades: course_grade = input('Enter grade (hit Enter if done): ') while course_grade not in ('A','B','C','D','F',empty_str): course_grade = input('Enter letter grade received: ') if course_grade == empty_str: more_grades = False else: num_credits = int(input('Enter number of credits: ')) semester_info.append([num_credits, course_grade]) return semester_info # ---- main # program greeting print('This program will determine the current semester GPA needed' + \ 'to attain \na specific cumulative GPA.') # get current GPA info total_credits = int(input('\nEnter total number of earned credits: ')) cumulative_gpa = float(input('Enter your current cumulative GPA: ')) # get current semester grade info print() current_sem_credits = \ (int(input('Enter total number of credits for this semester: '))) target_cumulative_gpa = float(input('Enter target cummulative GPA: ')) # calculate required semester GPA req_semester_gpa = \ (target_cumulative_gpa * (total_credits + current_sem_credits) - \ (cumulative_gpa * total_credits)) / current_sem_credits Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 30 # check if new cumulative GPA attainable if req_semester_gpa > 4.0: highest_cumulative_gpa = (cumulative_gpa * total_credits + \ 4.0 * current_sem_credits) / +\ (total_credits + current_sem_credits) print('The highest cummulative GPA you can achieve this semester is', format(highest_cumulative_gpa, '.2f')) else: print('\nIn order to attain a new cumulative GPA of', target_cumulative_gpa, ',\nyour GPA this', 'semester must be', format(req_semester_gpa, '.2f'), 'or better.') This program will determine the current semester GPA neededto attain a specific cumulative GPA. Enter total number of earned credits: 30 Enter your current cumulative GPA: 3.2 Enter total number of credits for this semester: 15 Enter target cummulative GPA: 3.4 In order to attain a new cumulative GPA of 3.4 , your GPA this semester must be 3.80 or better. >>> ================================ RESTART ================================ >>> This program will determine the current semester GPA neededto attain a specific cumulative GPA. Enter total number of earned credits: 60 Enter your current cumulative GPA: 3.35 Enter total number of credits for this semester: 15 Enter target cummulative GPA: 3.5 The highest cummulative GPA you can achieve this semester is 3.48 >>> Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 31 D3. Tic-Tac-Toe Two-Player Program Develop and test a Python program that lets two players play tic-tac-toe. Let player 1 be X and player 2 be O. Devise a method for each player to indicate where they wish to place their symbol. The program should terminate if either there is a winner, or if the game results in a tie. The tic-tactoe board should be displayed after every move as shown below. # Problem D3 (Chapter 5) # This program will allow two players to play the game of tic-tac-toe. def displayBoard(board): empty_str = '' for k in range(0, len(board)): symbol = board[k] if symbol == empty_str: symbol = '-' print(format(symbol, '^3'), end='') if (k + 1) % 3 == 0: print() print() def getMove(board, locations, player): empty_str = '' valid_move = False while not valid_move: move = input(player + ', ' + 'enter your move: ') if move not in locations: print('Must enter 1 .. 9') elif board[int(move) - 1] != empty_str: print('That location of the board already used') else: valid_move = True return move def win(board, symbol): empty_str = '' player_win = False if symbol == 'X': winning_sum = 6 else: winning_sum = 3 # recreate board with 1 for 'X' and 0 for 'O' alt_board = [2 if k == 'X' else 1 if k == 'O' else 0 for k in board] # search board for win k = 0 Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 32 while not player_win and k < 9: # row win? if alt_board[k] + alt_board[k + 1] + alt_board[k + 2] == winning_sum: player_win = True else: k = k + 3 if not player_win: k = 0 while not player_win and k < 3: # col win? if alt_board[k] + alt_board[k + 3] + alt_board[k + 6] == winning_sum: player_win = True else: k = k + 1 if not player_win: # diag win? if alt_board[0] + alt_board[4] + alt_board[8] == winning_sum or \ alt_board[2] + alt_board[4] + alt_board[6] == winning_sum: player_win = True return player_win def tieGame(board): empty_str = '' tie_game = True for loc in board: if loc == empty_str: tie_game = False return tie_game # ---- main # init empty_str = '' board = [empty_str for k in range(1, 10)] locations = [str(x) for x in range(1,10)] # program greeting print('This program will allow two players to play the game of tic-tac-toe.') print("Player 1 has 'X', and player 2 has 'O'.") # get players name_player1 = input('Enter the name of player 1: ') name_player2 = input('Enter the name of player 2: ') # display board locations print('Enter your mark using the board positions shown below.\n') displayBoard(locations) # start game player = name_player1 player_symbol = 'X' print(name_player1, "you start. You are playing 'X'") displayBoard(board) game_over = False while not game_over: move = getMove(board,locations, player) board[int(move) - 1] = player_symbol Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 33 displayBoard(board) if win(board, player_symbol): print(player + ', ' + 'you win!') game_over = True elif tieGame(board): print('Tie Game!') game_over = True else: if player == name_player1: player = name_player2 player_symbol = '0' else: player = name_player1 player_symbol = 'X' This program will allow two players to play the game of tic-tac-toe. Player 1 has 'X', and player 2 has 'O'. Enter the name of player 1: Chuck Enter the name of player 2: Steve Enter your mark using the board positions shown below. 1 4 7 2 5 8 3 6 9 Chuck you start. You are playing 'X' - - - - - - Chuck, X - - - enter your move: 1 - Steve, X 0 - - enter your move: 4 - Chuck, enter your move: 1 That location of the board already used Chuck, enter your move: 2 X X 0 - - - Steve, X X 0 0 - - enter your move: 5 - Chuck, X X 0 0 - - enter your move: 9 X Steve, X X 0 0 0 - enter your move: 7 X Chuck, X X 0 0 0 - enter your move: 3 X X Chuck you win! >>> Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 34 D4. Tic-Tac-Toe Automated Play (solution omitted) Introduction to Computer Science Using Python – Dierbach Copyright 2013 John Wiley and Sons 35