The inspiration for this program comes from my Introduction to Computer Science class at UVA. For some background, I have recently entered and fallen in love with the world of computer science, coding incessantly in Python in my spare time. I try to engage with the course content as much as possible to foster this love, and we were recently introduced to the concept of dictionaries and given an assignment to construct a grade book. I decided to use this opportunity to think as outside-of-the-box as I could in terms of how I could utilize dictionaries to efficiently accomplish the only vaguely-explained task of constructing a weighted gradebook. My passion for problem-solving and creative thinking made this my most enjoyable programming experience yet as I needed to grapple with a lot deep and layered algorithms when writing it.
The program uses two functions--assignment and total--which interact to compute a cumulative course grade given differing weights of assignment types and the assignments in them. The assignment function takes parameters of assignment type, the grade on it, and its weight relative to other assignments (e.g. 2 times the weight of other assignments). Assignment computes a running total for the weighted average of the assignment type given assignments in the type. There is one assignment per function call. The function keeps track of stats such as the cumulative values of the weight parameter, the running total for the weighted average, and a triple nested dictionary that keeps track of grade:weight pairs so they can be recalculated each function execution. The important yield from this function is the manipulation of a global dictionary that can contain different assignment types as keys and what their present running totals are for average grade (with weighted assignments).
The total function then takes as a parameter a dictionary with keys as assignment types and values of the type's weight in a course to calculate the overall grade by applying the assignment type's weighted average grade from the global dictionary in the assignment function with the weights in total function's dictionary parameter (If total's parameter contains an assignment type/key not found in assignment's yielded global dictionary, the assignments in that type are assumed to all be 0--thus averaging 0).
The brainstorming process was arduous. Since I would need a way to store multiple values such as the cumulative weight parameter values, the running total, and a grade:weight dictionary of all the assignments in a type for each assignment type, I realized that these values must be stored in a dictionary within an initial global dictionary so that they would be distinct for each assignment type. From there, the most important part was manipulating the grade:weight (triple nested) dictionary of all the assignments in a type so that the weights were accurate given the new call to the assignment function. This was done by dividing the values for parameter weight (representing weight relative to other assignments) by the running total for the cumulative weight. The grades (keys) were then multiplied by their new weights (values) and summed to produce the current weighted average for each assignment type.
The total function would then serve the culminating task of using the weighted average for each assignment type and applying it to the weight of the type within the whole course. This was done by iterating through the keys/types of the parameter proportions and checking if they were in the yielded global dictionary from the assignment function. If so, an array was filed with the products of assignment type course weights and their weighted average grade and this array was summed to yield the overall course grade.
A challenge presented to me in the program is dealing with the exception that would be thrown should a grade be entered in the assignment function that had already been sent into the assignment function in a previous call. The use of global variables and dictionaries created this problem since the program's triple-nested dictionary as mentioned before keeps a running collection of the grade:weight for each assignment type. There cannot be identical keys in a dictionary (e.g. there cannot be 2 different entries with key '100' in the dictionary). In order to resolve this, I coerced the grade parameter to a string. I used an algorithm whereby if parameter grade were in the triple-nested dictionary at that moment and were not a decimal, a ".0" would be added to it and 0s would continue being added until this decimal string was not a key in the dictionary; this is in the case that the parameter is an integer then coerced to a string. If the grade parameter were a decimal then coerced to a string, a '0' would be added until the decimal string was not a key in the dictionary.
What I feel most accomplished about in this program is the complexity and versatility of the use of dictionaries. To me, it represents the extra effort and steps that I take to truly master CS concepts out of my passion and enjoyment in the field. I am proud of my system for computing the weighted average using manipulations of that triple-nested dictionary of grades and their original weights (relative to other assignments) and then modifying those weights by dividing by a cumulative weight parameter total for each assignment. I am proud of my methods of exception handling explained in the challenges portion and I am proud of the robustness of the program in general in yielding a cumulative grade for a course. This program would serve as an ideal method for teachers and professors to construct weighted averages for students in courses as--especially in college courses--assignments are categorized by type and have weights, with individual assignments in them having their own weight (e.g. hw vs. midterms or midterms vs. finals).
This project allowed me to engage with a concept I learned in CS lecture at a level deeper than I have ever delved into with any other concept. Exploring nested dictionaries and manipulation of them as well as how global variables/dictionaries are built upon through these functions to yield the final cumulative grade were incredibly engaging. I am excited to engage with CS concepts from this point on with the same level of depth and complexity.
The future for Gradebook for Teachers - A Unique Approach to Dictionaries lies in its applications beyond gradebooks. This system for weighted averages using dictionaries can be used anywhere weighted averages are used. This includes examples where sampling of different populations with varying population sizes is done to construct some cumulative statistic. Furthermore, the program in context of grade books can be made more user friendly. This includes more exception handling for parameters to the total function and assignment function that may be the same assignment type as an existing assignment type key in the dictionary, but are not exactly typed the same (e.g. spelling, uppercase/lowercase, alternative names).
Try It out