From 8e4dbfd5dcb1c70384822cad509dace238357b84 Mon Sep 17 00:00:00 2001 From: kiritofeng Date: Mon, 2 Sep 2019 08:47:21 -0400 Subject: [PATCH] Use `Decimal` in floats checker --- dmoj/checkers/floats.py | 15 +++++++++++---- 1 file changed, 11 insertions(+), 4 deletions(-) diff --git a/dmoj/checkers/floats.py b/dmoj/checkers/floats.py index 4e519f3de..3bc4b19e3 100644 --- a/dmoj/checkers/floats.py +++ b/dmoj/checkers/floats.py @@ -1,3 +1,4 @@ +from decimal import Decimal from re import split as resplit from dmoj.error import InternalError @@ -27,7 +28,13 @@ def verify_default(process_float, judge_float, epsilon): abs(1.0 - process_float / judge_float) <= epsilon) -def check(process_output, judge_output, precision=6, error_mode='default', **kwargs): +def check(process_output, judge_output, precision=6, fast=True, error_mode='default', **kwargs): + + if fast: + float_datatype = float + else: + float_datatype = Decimal + # Discount empty lines process_lines = list(filter(None, resplit(b'[\r\n]', utf8bytes(process_output)))) judge_lines = list(filter(None, resplit(b'[\r\n]', utf8bytes(judge_output)))) @@ -44,7 +51,7 @@ def check(process_output, judge_output, precision=6, error_mode='default', **kwa if not verify_float: raise InternalError('invalid `error_mode` value') - epsilon = 10 ** -int(precision) + epsilon = float_datatype(10) ** -int(precision) try: for process_line, judge_line in zip(process_lines, judge_lines): @@ -57,13 +64,13 @@ def check(process_output, judge_output, precision=6, error_mode='default', **kwa for process_token, judge_token in zip(process_tokens, judge_tokens): # Allow mixed tokens, for lines like "abc 0.68 def 0.70" try: - judge_float = float(judge_token) + judge_float = float_datatype(judge_token) except ValueError: # If it's not a float the token must match exactly if process_token != judge_token: return False else: - process_float = float(process_token) + process_float = float_datatype(process_token) if not verify_float(process_float, judge_float, epsilon): return False