-
Notifications
You must be signed in to change notification settings - Fork 77
Session 5 Homework #67
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Changes from all commits
3299afc
a8811a1
7e0ce52
431c31d
7154c31
d52e9de
fedcecd
afc4e56
6dffbc1
30e49f4
File filter
Filter by extension
Conversations
Jump to
Diff view
Diff view
There are no files selected for viewing
| Original file line number | Diff line number | Diff line change |
|---|---|---|
|
|
@@ -162,4 +162,3 @@ | |
| fruits.pop() | ||
| print fruits | ||
| print fruitsCopy | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,31 @@ | ||
|
|
||
| ''' | ||
| The raw_input() function can generate two exceptions: EOFError or KeyboardInterrupt on end-of-file(EOF) or canceled input. | ||
| Create a wrapper function, perhaps safe_input() that returns None rather rather than raising these exceptions, when | ||
| the user enters ^C for Keyboard Interrupt, or ^D (^Z on Windows) for End Of File. | ||
| Update your mailroom program to use exceptions (and IBAFP) to handle malformed numeric input | ||
| ''' | ||
|
|
||
| def safe_input(prompt): | ||
| try: | ||
| input = raw_input(prompt) | ||
| except EOFError: | ||
| print "That won't work!" | ||
| return None | ||
| except KeyboardInterrupt: | ||
| print "HAHAHAHA... you're stuck forever" | ||
| return None | ||
| return input | ||
|
|
||
|
|
||
| if __name__ == "__main__": | ||
| trapped = True | ||
| while trapped: | ||
| trapString = safe_input("Try to get out: ") | ||
| if trapString is not None: | ||
| print "You wrote:", trapString | ||
| if trapString.upper() == 'Q': | ||
| trapped = False | ||
| else: | ||
| print "Would you like to play a game?" | ||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,92 @@ | ||
| ''' | ||
| Create a dictionary containing "name", "city", and "cake" for "Chris" from "Seattle" who likes "Chocolate". | ||
| Display the dictionary. | ||
|
|
||
| Delete the entry for "cake" | ||
| Display the dictionary. | ||
|
|
||
| Add an entry for "fruit" with "Mango" and display the dictionary. | ||
| Display the dictionary keys. | ||
|
|
||
| Display the dictionary values. | ||
|
|
||
| Display whether or not "cake" is a key in the dictionary (i.e. False) (now). | ||
|
|
||
| Display whether or not "Mango" is a value in the dictionary (i.e. True). | ||
|
|
||
| Using the dict constructor and zip, build a dictionary of numbers from zero to fifteen and the hexadecimal equivalent (string is fine). | ||
|
|
||
| Using the dictionary from item 1: Make a dictionary using the same keys but with the number of ts in each value. | ||
|
|
||
| Create sets s2, s3 and s4 that contain numbers from zero through twenty, divisible 2, 3 and 4. | ||
|
|
||
| Display the sets. | ||
|
|
||
| Display if s3 is a subset of s2 (False) | ||
|
|
||
| and if s4 is a subset of s2 (True). | ||
| Create a set with the letters in Python and add i to the set. | ||
| Create a frozenset with the letters in marathon | ||
| display the union and intersection of the two sets. | ||
|
|
||
| ''' | ||
|
|
||
| if __name__ == "__main__": | ||
| d = {"name":"Chris", "city":"Seattle", "cake":"Chocolate"} | ||
| print d | ||
|
|
||
| d.pop('cake') | ||
| print d | ||
|
|
||
| d['fruit'] = 'Mango' | ||
| print d | ||
|
|
||
| print d.values() | ||
|
|
||
| print d.has_key('cake') | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. you can also do: a touch simpler |
||
| print 'Mango' in d.values() | ||
|
|
||
| nums = (0, 1, 2, 3, 4, 5, 6, 7, 8, 9, 10, 11, 12, 13,14, 15) | ||
| hexes = ('0x0', '0x1', '0x2', '0x3', '0x4','0x5', '0x6', '0x7', '0x8', '0x9', '0xa', '0xb', '0xc', '0xd', '0xe', '0xf') | ||
| hexdict = dict (zip(nums, hexes)) | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. you got the key point. but python has a built-in hex() function that will create a hex strings from a value for you. |
||
| print hexdict | ||
|
|
||
| for key in d: | ||
| d[key] = d[key].count('t') | ||
| print d | ||
|
|
||
| #Create sets s2, s3 and s4 that contain numbers from zero through twenty, divisible 2, 3 and 4. | ||
| s2 = set() | ||
| s3 = set() | ||
| s4 = set() | ||
| for i in range (0,21): | ||
| if i % 2 == 0: | ||
| s2.add(i) | ||
| if i % 3 == 0: | ||
| s3.add(i) | ||
| if i % 4 == 0: | ||
| s4.add(i) | ||
| print s2 | ||
| print s3 | ||
| print s4 | ||
|
|
||
| #Display if s3 is a subset of s2 (False) | ||
| print s3.issubset(s2) | ||
|
|
||
| #and if s4 is a subset of s2 (True). | ||
| print s4.issubset(s2) | ||
|
|
||
| #Create a set with the letters in Python and add i to the set. | ||
| py = set(list('python')) | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. no need for the list() call here -- a string is already a sequence of characters. |
||
| py.add('i') | ||
| print py | ||
|
|
||
| #Create a frozenset with the letters in marathon | ||
| fs = frozenset (list('marathon')) | ||
| print fs | ||
|
|
||
| #display the union and intersection of the two sets. | ||
| print py.union(fs) | ||
| print py.intersection(fs) | ||
|
|
||
|
|
||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,188 @@ | ||
| """ | ||
|
|
||
| Dave Fugelso, UW Python Course (Developing on Windows so didn't make this an executable script.) | ||
|
|
||
| UPDATED: For Session 4. | ||
|
|
||
| 1. Uses ValueError exception on numeric input | ||
| 2. Uses sum to calculate total donations (Just a fix from last week) | ||
| 3. Uses a Dict to hold donor names instead of a list. Key is donor name and value is list of donations. | ||
| 4. Remove unnecessary line continuations in Donors initialization. | ||
|
|
||
| And, | ||
|
|
||
| 5. Write a full set of letters to everyone to individual files on disk | ||
| 6. See if you can use a dict to switch between the users selections | ||
| 7. Try to use a dict and the .format() method to do the letter as one big template -- rather than building up a big string in parts. | ||
|
|
||
|
|
||
| Mail Room | ||
|
|
||
| You work in the mail room at a local charity. Part of your job is to write incredibly boring, repetitive emails thanking your donors for their generous gifts. | ||
| You are tired of doing this over an over again, so yo've decided to let Python help you out of a jam. | ||
|
|
||
| Write a small command-line script called mailroom.py. As with Task 1, This script should be executable. The script should accomplish the following goals: | ||
|
|
||
| It should have a data structure that holds a list of your donors and a history of the amounts they have donated. This structure should be populated at | ||
| first with at least five donors, with between 1 and 3 donations each | ||
| The script should prompt the user (you) to choose from a menu of 2 actions: 'Send a Thank You' or 'Create a Report'. | ||
| If the user (you) selects 'Send a Thank You', prompt for a Full Name. | ||
| If the user types 'list', show them a list of the donor names and re-prompt | ||
| If the user types a name not in the list, add that name to the data structure and use it. | ||
| If the user types a name in the list, use it. | ||
| Once a name has been selected, prompt for a donation amount. | ||
| Verify that the amount is in fact a number, and re-prompt if it isn't. | ||
| Once an amount has been given, add that amount to the donation history of the selected user. | ||
| Finally, use string formatting to compose an email thanking the donor for their generous donation. Print the email to the terminal and return to the original prompt. | ||
| It is fine to forget new donors once the script quits running. | ||
|
|
||
| If the user (you) selected 'Create a Report' Print a list of your donors, sorted by total historical donation amount. | ||
| Include Donor Name, total donated, number of donations and average donation amount as values in each row. | ||
| Using string formatting, format the output rows as nicely as possible. The end result should be tabular (values in each column should align with those above and below) | ||
| After printing this report, return to the original prompt. | ||
| At any point, the user should be able to quit their current task and return to the original prompt. | ||
| From the original prompt, the user should be able to quit the script cleanly | ||
| First, factor your script into separate functions. Each of the above tasks can be accomplished by a series of steps. Write discreet functions that accomplish individual steps and call them. | ||
|
|
||
| Second, use loops to control the logical flow of your program. Interactive programs are a classic use-case for the while loop. | ||
|
|
||
| Put the functions you write into the script at the top. | ||
|
|
||
| Put your main interaction into an if __name__ == '__main__' block. | ||
|
|
||
| Finally, use only functions and the basic Python data types you've learned about so far. There is no need to go any farther than that for this assignment. | ||
|
|
||
| As always, put the new file in your student directory in a session03 directory, and add it to your clone early. Make frequent commits with good, clear messages about what you are doing and why. | ||
|
|
||
| When you are done, push your changes and make a pull request. | ||
| """ | ||
|
|
||
| import operator | ||
| import datetime | ||
|
|
||
| #Donor list | ||
|
|
||
| donors = { 'Dave Fugelso': [3000, 6000, 4000], | ||
| 'Barb Grecco': [5000], | ||
| 'Ken Johnson': [500, 250, 50, 80], | ||
| 'Jack Bell': [55, 55, 55, 55, 55], | ||
| 'Alejandro Escobar': [25, 25] | ||
| } | ||
|
|
||
| def listDonors (): | ||
| ''' | ||
| List donors. | ||
| ''' | ||
| for key in donors: | ||
| print key, donors[key] | ||
|
|
||
| def report (): | ||
| ''' | ||
| Create a report with Name, Total Donation, Number of Donation and average donation size. Print largest donor first. | ||
| ''' | ||
|
|
||
| # go through list and calculate donor metrics | ||
| for key in donors: | ||
| print key, donors[key], sum(donors[key]) | ||
|
|
||
| #print it out | ||
| print '\n\nDonor\t\t\t\tAmount\t\tNumber of Donations\t\tAverage Donation' | ||
| print '-----\t\t\t\t------\t\t-------------------\t\t----------------' | ||
|
|
||
| # Sorting a dict by sum of the values... kinda tough. Fond a great lambda func to do that on Stack Overflow, but | ||
| # in the spirit of not getting to far out from the current topic, going to create a list and use the same sort. | ||
|
|
||
| # iterate over the dictionary and create a list of donor, totals | ||
| #Check here later to see f we can geta list of keys without iterating.... TBD | ||
| sortlist = list() | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. I usally see: sortlist = [] though it does do the same thing. |
||
| for key in donors: | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. sure: donors. keys() is a list of the keys. |
||
| sortlist.append ( key ) | ||
|
|
||
| for donorName in sorted(sortlist, key=lambda individual: sum(donors[individual]), reverse=True): | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. nice! |
||
| print donorName, | ||
| if len(donorName) < 15: | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. as you can see, formatting with tabs is a nightmare -- Id do just spaces.
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. oh -- and even with the pain you've gone through, it would break on most *nix terminals -- they generally use 8 spaces per tab be default... |
||
| print '\t\t\t', | ||
| else: | ||
| print '\t\t', | ||
| print sum(donors[donorName]), | ||
| print '\t\t\t', | ||
| if len(donors[donorName]) > 0: | ||
| print len(donors[donorName]), | ||
| print '\t\t\t', | ||
| print sum(donors[donorName]) / len(donors[donorName]) | ||
| else: | ||
| print '0\t\tNA' | ||
| print '\n\n\n\n' | ||
|
|
||
| def thankYou (fullname, donations): | ||
| ''' | ||
| Send off a thank you note to a single donor. | ||
| ''' | ||
| print '\n\n\n\n\t\t\t\t\t',datetime.date.today() | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. nice job finding datetime! |
||
| print '\nOur Charity Name\nAddress\nEtc\n\n\n' | ||
| name = fullname.split() | ||
| print 'Dear '+name[0]+':\n' | ||
| if len(donations) <= 1: | ||
| print 'Thank you for your donation of ', | ||
| print donations[0] | ||
| print '.' | ||
| else: | ||
| print 'Thank you for your donations of ', | ||
| for i in range (0, len(donations)-1): | ||
| print donations[i], | ||
| print ',', | ||
| print ' and ', | ||
| print donations[len(donations)-1], | ||
| print '.' | ||
| print '\nWe look forward to serving our community blah blah blah.\n\nSincerely, \n\nOur Charity.\n\n\n\n' | ||
|
|
||
| def addDonor (name): | ||
| ''' | ||
| Add <name> to the list of donors and get the amounts of donation. | ||
| ''' | ||
| donations = [] | ||
| amount = 0 | ||
| while amount >= 0: | ||
| inp = raw_input ('Add amount of donation one at a time. Enter \'-1\' to finish: ') | ||
| try: | ||
| amount = int(inp) | ||
| if amount > 0: | ||
| donations.append(amount) | ||
| except ValueError: | ||
| print ('Input must be a number.') | ||
| amount = 0 | ||
| donors[name] = donations | ||
|
|
||
|
|
||
|
|
||
|
|
||
| def processDonors (): | ||
| ''' | ||
| Interact with administrator to manage donor list. | ||
| ''' | ||
| processing = True | ||
| while processing: | ||
| action = raw_input ("Select 'Send a Thank You(S)', 'Create a report(C)', or 'Quit(Q)': ") | ||
| if action.upper() == 'S' or action.upper() == 'SEND A THANK YOU': | ||
| thankYouProcessing = True | ||
| while thankYouProcessing: | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. maybe a bit better to put the thankYouProcessing in a separate function -- if it were any more complicated or deeply nested, you'd want to keep it clean. |
||
| name = raw_input ("Enter name of donor, add a donor ('A') or ('Add'), or list all donors ('L') or ('List') or 'E' or 'End' to go to main menu: ") | ||
| if name.upper() == 'L' or name.upper() == 'LIST': | ||
| listDonors() | ||
| elif name.upper() == 'E' or name.upper() == 'END': | ||
| thankYouProcessing = False | ||
| else: | ||
| if name in donors.keys(): | ||
| thankYou (name, donors[name]) | ||
| else: | ||
| addDonor(name) | ||
| elif action.upper() == 'Q' or action.upper == 'QUIT': | ||
| processing = False | ||
| elif action.upper() == 'C' or action.upper == 'Create a report'.upper(): | ||
| report() | ||
| else: | ||
| print 'Unrecognized input.' | ||
|
|
||
|
|
||
| if __name__ == "__main__": | ||
| processDonors () | ||
| Original file line number | Diff line number | Diff line change |
|---|---|---|
| @@ -0,0 +1,49 @@ | ||
| ''' | ||
| Paths and File Processing | ||
| -------------------------- | ||
|
|
||
| * write a program which prints the full path to all files in the current directory, one per line | ||
|
|
||
| * write a program which copies a file from a source, to a destination (without using shutil, or the OS copy command) | ||
| ''' | ||
|
|
||
| import os | ||
|
|
||
| def myFileCopy (source, destination): | ||
| ''' | ||
| Copy a file by reading the content and then writing them. | ||
| ''' | ||
| try: | ||
| file_in = open(source, 'r') | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. careful -- in the general case, you want tus binary mode: |
||
| except FileNotFoundError: | ||
| print 'File not found' | ||
| return | ||
|
|
||
| try: | ||
| file_out = open(destination, 'w') | ||
| except FileExistsError: | ||
| print 'Unable to create file' | ||
| return | ||
|
|
||
|
|
||
| for line in file_in: | ||
| file_out.write(line) | ||
|
|
||
| file_out.close() | ||
| file_in.close() | ||
|
|
||
|
|
||
| def printFullPathInCurrentDirectory(): | ||
| ''' | ||
| Print all filenames in the current directory. | ||
| ''' | ||
| path = os.path.dirname(os.path.abspath(__file__)) | ||
| for (dirpath, dirnames, filenames) in os.walk(path): | ||
|
Contributor
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. very slick! I was only looking for os.listdir(), but this is clearly more complete! |
||
| for fname in filenames: | ||
| print os.path.join(path, fname) | ||
|
|
||
| if __name__ == "__main__": | ||
| printFullPathInCurrentDirectory() | ||
| myFileCopy ('t.t', 't.a') | ||
|
|
||
|
|
||
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
good point -- this may not be the best idea in production code....
But you got the basics of using Exceptions down -- that's the point.