on perhaps unloading modules?

Hope Rouselle hrouselle at jevedi.com
Sun Aug 15 11:48:20 EDT 2021


Hope Rouselle <hrouselle at jevedi.com> writes:

> Hope Rouselle <hrouselle at jevedi.com> writes:
>
> [...]
>
>> Of course, you want to see the code.  I need to work on producing a
>> small example.  Perhaps I will even answer my own question when I do.
>
> [...]
>
> Here's a small-enough case.  We have two students here.  One is called
> student.py and the other is called other.py.  They both get question 1
> wrong, but they --- by definition --- get question 2 right.  Each
> question is worth 10 points, so they both should get losses = 10.
>
> (*) Student student.py
>
> def question1(t): # right answer is t[2]
>   return t[1] # lack of attention, wrong answer
>
>
> (*) Student other.py
>
> def question1(t): # right answer is t[2]
>   return t[0] # also lack of attention, wrong answer
>
>
> (*) Grading
>
> All is good on first run.
>
> Python 3.5.2 [...] on win32
> [...]
>>>> reproducible_problem()
> student.py, total losses 10
> other.py, total losses 10
>
> The the problem:
>
>>>> reproducible_problem()
> student.py, total losses 0
> other.py, total losses 0
>
> They lose nothing because both modules are now permanently modified.
>
> (*) The code of grading.py
>
> # -*- mode: python; python-indent-offset: 2 -*-
> def key_question1(t): 
>   # Pretty simple.  Student must just return index 2 of a tuple.
>   return t[2]
>
> def reproducible_problem(): # grade all students
>   okay, m = get_student_module("student.py")
>   r = grade_student(m)
>   print("student.py, total losses", r) # should be 10
>   okay, m = get_student_module("other.py")
>   r = grade_student(m)
>   print("other.py, total losses", r) # should be 10
>
> def grade_student(m): # grades a single student
>   losses  = question1_verifier(m)
>   losses += question2_verifier(m)
>   return losses
>
> def question1_verifier(m):
>   losses = 0
>   if m.question1( (0, 1, 2, 3) ) != 2: # wrong answer
>     losses = 10
>   return losses
>
> def question2_verifier(m):
>   m.question1 = key_question1
>   # To grade question 2, we overwrite the student's module by giving
>   # it the key_question1 procedure.  This way we are able to let the
>   # student get question 2 even if s/he got question 1 incorrect.
>   losses = 0
>   return losses 

My solution is to painfully save each original procedure from student in
a variable, replace them with the key's, then restore them at the end.
I couldn't overwrite m.__dict__ because it is readonly.  (Didn't find a
neater's way out.)

def question2_verifier(m):
  question1_original = m.question1
  m.question1 = key_question1
  # apply verifications... 
  m.question1 = question1_original
  return losses


More information about the Python-list mailing list