
'''simple docstring'''





import math
import time
from typing import Dict, List, Optional

from torch.utils.data import Dataset

from transformers import SeqaSeqTrainer, is_torch_tpu_available
from transformers.trainer_utils import PredictionOutput, speed_metrics


if is_torch_tpu_available(check_device=False):
		import torch_xla.core.xla_model as xm
		import torch_xla.debug.metrics as met





class       __A(				UpperCAmelCase       ):

					def __init__(	self					:     List[str]   ,					*__UpperCamelCase					:     Union[str, Any]   ,					__UpperCamelCase					:     Dict=None   ,					__UpperCamelCase					:     Tuple=None   ,					**__UpperCamelCase					:     Optional[Any]   ):
												super().__init__(*__UpperCamelCase   ,					**__UpperCamelCase   )
												lowerCamelCase_							  =					eval_examples
												lowerCamelCase_							  =					post_process_function

					def    lowercase__      (	self					:     int   ,					__UpperCamelCase					:     Optional[Dataset] = None   ,					__UpperCamelCase					:     List[str]=None   ,					__UpperCamelCase					:     Optional[List[str]] = None   ,					__UpperCamelCase					:     str = "eval"   ,					**__UpperCamelCase					:     List[str]   ,					):
												lowerCamelCase_							  =					gen_kwargs.copy()
												lowerCamelCase_							  =					(
												    gen_kwargs["""max_length"""] if gen_kwargs.get("""max_length"""   ) is not None else self.args.generation_max_length
												)
												lowerCamelCase_							  =					(
												    gen_kwargs["""num_beams"""] if gen_kwargs.get("""num_beams"""   ) is not None else self.args.generation_num_beams
												)
												lowerCamelCase_							  =					gen_kwargs

												lowerCamelCase_							  =					self.eval_dataset if eval_dataset is None else eval_dataset
												lowerCamelCase_							  =					self.get_eval_dataloader(__UpperCamelCase   )
												lowerCamelCase_							  =					self.eval_examples if eval_examples is None else eval_examples

												# Temporarily disable metric computation, we will do it in the loop here.
												lowerCamelCase_							  =					self.compute_metrics
												lowerCamelCase_							  =					None
												lowerCamelCase_							  =					time.time()
												lowerCamelCase_							  =					self.prediction_loop if self.args.use_legacy_prediction_loop else self.evaluation_loop
												try:
																			lowerCamelCase_							  =					eval_loop(
																			    __UpperCamelCase   ,					description="""Evaluation"""   ,					prediction_loss_only=True if compute_metrics is None else None   ,					ignore_keys=__UpperCamelCase   ,					metric_key_prefix=__UpperCamelCase   ,					)
												finally:
																			lowerCamelCase_							  =					compute_metrics
												lowerCamelCase_							  =					self.args.eval_batch_size * self.args.world_size
												if F'''{metric_key_prefix}_jit_compilation_time''' in output.metrics:
																			start_time += output.metrics[F'''{metric_key_prefix}_jit_compilation_time''']
												output.metrics.update(
												    speed_metrics(
												        __UpperCamelCase   ,					__UpperCamelCase   ,					num_samples=output.num_samples   ,					num_steps=math.ceil(output.num_samples / total_batch_size   )   ,					)   )

												if self.post_process_function is not None and self.compute_metrics is not None and self.args.should_save:
																			# Only the main node write the results by default
																			lowerCamelCase_							  =					self.post_process_function(__UpperCamelCase   ,					__UpperCamelCase   ,					__UpperCamelCase   )
																			lowerCamelCase_							  =					self.compute_metrics(__UpperCamelCase   )

																			# Prefix all keys with metric_key_prefix + '_'
																			for key in list(metrics.keys()   ):
																										if not key.startswith(F'''{metric_key_prefix}_'''   ):
																																	lowerCamelCase_							  =					metrics.pop(__UpperCamelCase   )

																			metrics.update(output.metrics   )
												else:
																			lowerCamelCase_							  =					output.metrics

												if self.args.should_log:
																			# Only the main node log the results by default
																			self.log(__UpperCamelCase   )

												if self.args.tpu_metrics_debug or self.args.debug:
																			# tpu-comment: Logging debug metrics for PyTorch/XLA (compile, execute times, ops, etc.)
																			xm.master_print(met.metrics_report()   )

												lowerCamelCase_							  =					self.callback_handler.on_evaluate(self.args   ,					self.state   ,					self.control   ,					__UpperCamelCase   )
												return metrics



					def    lowercase__      (	self					:     int   ,					__UpperCamelCase					:     Union[str, Any]   ,					__UpperCamelCase					:     Optional[int]   ,					__UpperCamelCase					:     List[Any]=None   ,					__UpperCamelCase					:     str = "test"   ,					**__UpperCamelCase					:     Tuple   ):
												lowerCamelCase_							  =					gen_kwargs.copy()

												lowerCamelCase_							  =					self.get_test_dataloader(__UpperCamelCase   )

												# Temporarily disable metric computation, we will do it in the loop here.
												lowerCamelCase_							  =					self.compute_metrics
												lowerCamelCase_							  =					None
												lowerCamelCase_							  =					time.time()
												lowerCamelCase_							  =					self.prediction_loop if self.args.use_legacy_prediction_loop else self.evaluation_loop
												try:
																			lowerCamelCase_							  =					eval_loop(
																			    __UpperCamelCase   ,					description="""Prediction"""   ,					prediction_loss_only=True if compute_metrics is None else None   ,					ignore_keys=__UpperCamelCase   ,					metric_key_prefix=__UpperCamelCase   ,					)
												finally:
																			lowerCamelCase_							  =					compute_metrics

												lowerCamelCase_							  =					self.args.eval_batch_size * self.args.world_size
												if F'''{metric_key_prefix}_jit_compilation_time''' in output.metrics:
																			start_time += output.metrics[F'''{metric_key_prefix}_jit_compilation_time''']
												output.metrics.update(
												    speed_metrics(
												        __UpperCamelCase   ,					__UpperCamelCase   ,					num_samples=output.num_samples   ,					num_steps=math.ceil(output.num_samples / total_batch_size   )   ,					)   )
												if self.post_process_function is None or self.compute_metrics is None:
																			return output

												lowerCamelCase_							  =					self.post_process_function(__UpperCamelCase   ,					__UpperCamelCase   ,					__UpperCamelCase   ,					"""predict"""   )
												lowerCamelCase_							  =					self.compute_metrics(__UpperCamelCase   )

												# Prefix all keys with metric_key_prefix + '_'
												for key in list(metrics.keys()   ):
																			if not key.startswith(F'''{metric_key_prefix}_'''   ):
																										lowerCamelCase_							  =					metrics.pop(__UpperCamelCase   )
												metrics.update(output.metrics   )
												return PredictionOutput(predictions=predictions.predictions   ,					label_ids=predictions.label_ids   ,					metrics=__UpperCamelCase   )







from ..utils import DummyObject, requires_backends





class       __A(				metaclass=UpperCAmelCase       ):
					SCREAMING_SNAKE_CASE			    =    ['''torch''', '''scipy''']

					def __init__(	self					:     Any   ,					*__UpperCamelCase					:     str   ,					**__UpperCamelCase					:     Any   ):
												requires_backends(self   ,					["""torch""", """scipy"""]   )

					@classmethod
					def    lowercase__      (	cls					:     Dict   ,					*__UpperCamelCase					:     str   ,					**__UpperCamelCase					:     Dict   ):
												requires_backends(cls   ,					["""torch""", """scipy"""]   )



					@classmethod
					def    lowercase__      (	cls					:     str   ,					*__UpperCamelCase					:     Optional[int]   ,					**__UpperCamelCase					:     Optional[int]   ):
												requires_backends(cls   ,					["""torch""", """scipy"""]   )





