diff --git a/app/docs/user.md b/app/docs/user.md index 1e71f8f..ac555d0 100644 --- a/app/docs/user.md +++ b/app/docs/user.md @@ -2,6 +2,8 @@ This function is used to compare two number arrays/vectors/matrices, provided absolute and/or relative tolerance parameters `rtol` and `atol`. This is carried out using the [numpy.allclose](https://numpy.org/doc/stable/reference/generated/numpy.allclose.html) function. +If the answer is not an array of numbers an exception is raised. If the response is not an array of numbers, a feedback message that informs the user that only numbers are accepte will be generated. + ### Optional parameters There is one optional parameter: `feedback_for_incorrect_response`. diff --git a/app/evaluation.py b/app/evaluation.py index 6a14833..68669ed 100644 --- a/app/evaluation.py +++ b/app/evaluation.py @@ -23,29 +23,41 @@ def evaluation_function(response, answer, params) -> dict: to output the grading response. """ - answer_ok = process_element(answer) - if not answer_ok: + try: + process_element(answer) + except ValueError: + raise Exception("Answer has at least one field that is not a number.") + except Exception: raise Exception("Answer has empty fields.") - response_ok = process_element(response) - if not response_ok: + return {"is_correct": False} + + feedback = "" + try: + process_element(response) + except ValueError: + feedback = "Only numbers are permitted." + except Exception: + feedback = "Response has at least one empty field." + + if len(feedback) > 0: return { "is_correct": False, - "feedback": "Response has empty fields." + "feedback": feedback, } try: - res = np.array(response, dtype=np.float32) - except Exception as e: + ans = np.array(answer, dtype=np.float32) + except ValueError as e: raise EvaluationException( - f"Failed to parse user response", + f"Failed to parse correct answer", detail=repr(e) ) try: - ans = np.array(answer, dtype=np.float32) - except Exception as e: + res = np.array(response, dtype=np.float32) + except ValueError as e: raise EvaluationException( - f"Failed to parse correct answer", + f"Failed to parse response", detail=repr(e) ) @@ -65,14 +77,14 @@ def evaluation_function(response, answer, params) -> dict: def process_element(element): is_ok = True - if isinstance(element,list): + if isinstance(element, list): for e in element: - is_ok = process_element(e) + process_element(e) else: - if isinstance(element,str): + if isinstance(element, str): element = element.strip() if len(element) == 0 or "element" == "undefined": - is_ok = False + raise Exception("Contains an empty element") else: element = float(element) - return is_ok \ No newline at end of file + return \ No newline at end of file diff --git a/app/evaluation_tests.py b/app/evaluation_tests.py index ee26ec2..0a68fe8 100644 --- a/app/evaluation_tests.py +++ b/app/evaluation_tests.py @@ -44,7 +44,7 @@ def test_2D_empty_string_in_response(self): response = evaluation_function(response, answer, {}) self.assertEqual(response["is_correct"], False) - self.assertEqual(response["feedback"], "Response has empty fields.") + self.assertEqual(response["feedback"], "Response has at least one empty field.") def test_no_tolerance_correct(self): response = [1, 2] @@ -132,6 +132,26 @@ def test_2D_incorrect_with_custom_feedback(self): # # self.assertEqual(response.get("is_correct"), True) + def test_answer_not_array_of_numbers(self): + response = [[1, 1], [1, 1]] + answer = [[1, 1], [1, "a"]] + + self.assertRaises( + Exception, + evaluation_function, + response, + answer, + {}, + ) + + def test_response_not_array_of_numbers(self): + response = [[1, 1], [1, "a"]] + answer = [[1, 1], [1, 0]] + + response = evaluation_function(response, answer, {}) + + self.assertEqual(response.get("is_correct"), False) + self.assertEqual(response["feedback"], "Only numbers are permitted.") if __name__ == "__main__": unittest.main()