I have a class called 'Student' that creates a basic student object complete with everything needed to kick out a GPA. I have added two methods that deal with gradepoint and a letter grade respectively to then calculate a GPA. My question is what the best method and placement would be to add error handling in case they entered a letter grade that wasn't acceptable (i.e. G or X). Would I do that in the method itself, or is in the program calling it more appropriate?
class Student:
    def __init__(self, name, hours, qpoints):
        self.name = name
        self.hours = float(hours)
        self.qpoints = float(qpoints)
    def get_name(self):
        return self.name
    def get_hours(self):
        return self.hours
    def get_qpoints(self):
        return self.qpoints
    def gpa(self):
        return self.qpoints / self.hours
    def add_grade(self, grade_point, credit_hours):
        self.qpoints += grade_point * credit_hours
        self.hours += credit_hours
    def add_letter_grade(self, grade_letter, credit_hours):
        letter_grades = {
            'A': 4.0,
            'B': 3.0,
            'C': 2.0,
            'D': 1.0,
            'F': 0.0
        }
        grade_point = letter_grades.get(grade_letter)
        self.qpoints += grade_point * credit_hours
        self.hours += credit_hours
def main():
    new_student = Student('Mike Smith', 0, 0)
while True:
    usr_input = input('Please enter the student course information'
                      ' (grade and credit hours) separated'
                      ' by a comma <q to quit>: ')
    if usr_input == 'q':
        break
    else:
        grade, hours = usr_input.split(',')
        if grade.isalpha():
            new_student.add_letter_grade(grade, float(hours))
        else:
            new_student.add_grade(float(grade), float(hours))
print('{0}\'s final GPA was {1:.2f}'.format(new_student.get_name(), new_student.gpa()))
if __name__ == '__main__':
    main()
 
     
     
     
     
    