






"""simple docstring"""







import numpy as np

import datasets


__a       :	Any             = '\nCompute the Mahalanobis Distance\n\nMahalonobis distance is the distance between a point and a distribution.\nAnd not between two distinct points. It is effectively a multivariate equivalent of the Euclidean distance.\nIt was introduced by Prof. P. C. Mahalanobis in 1936\nand has been used in various statistical applications ever since\n[source: https://www.machinelearningplus.com/statistics/mahalanobis-distance/]\n'

__a       :	List[Any]             = '\\n@article{de2000mahalanobis,\n  title={The mahalanobis distance},\n  author={De Maesschalck, Roy and Jouan-Rimbaud, Delphine and Massart, D{\'e}sir{\'e} L},\n  journal={Chemometrics and intelligent laboratory systems},\n  volume={50},\n  number={1},\n  pages={1--18},\n  year={2000},\n  publisher={Elsevier}\n}\n'

__a       :	Union[str, Any]             = '\nArgs:\n    X: List of datapoints to be compared with the `reference_distribution`.\n    reference_distribution: List of datapoints from the reference distribution we want to compare to.\nReturns:\n    mahalanobis: The Mahalonobis distance for each datapoint in `X`.\nExamples:\n\n    >>> mahalanobis_metric = datasets.load_metric("mahalanobis")\n    >>> results = mahalanobis_metric.compute(reference_distribution=[[0, 1], [1, 0]], X=[[0, 1]])\n    >>> print(results)\n    {\'mahalanobis\': array([0.5])}\n'







@datasets.utils.file_utils.add_start_docstrings(_DESCRIPTION       , _KWARGS_DESCRIPTION							)
class        _SCREAMING_SNAKE_CASE						(  datasets.Metric							):





       """simple docstring"""





       def  lowercase		(   self:     List[str]    ):

            '''simple docstring'''

            return datasets.MetricInfo(
                description=_DESCRIPTION				,		citation=_CITATION				,		inputs_description=_KWARGS_DESCRIPTION				,		features=datasets.Features(
                    {
                        '''X''': datasets.Sequence(datasets.Value('''float'''				,		id='''sequence'''    )				,		id='''X'''    ),
                    }    )				,		)





       def  lowercase		(   self:     Optional[int]				,		__A:     int				,		__A:     List[str]    ):

            '''simple docstring'''

            a__          =  np.array(__A    )
            a__          =  np.array(__A    )

            # Assert that arrays are 2D
            if len(X.shape    ) != 2:
                 raise ValueError('''Expected `X` to be a 2D vector'''    )
            if len(reference_distribution.shape    ) != 2:
                 raise ValueError('''Expected `reference_distribution` to be a 2D vector'''    )
            if reference_distribution.shape[0] < 2:
                 raise ValueError(
                     '''Expected `reference_distribution` to be a 2D vector with more than one element in the first dimension'''    )

            # Get mahalanobis distance for each prediction
            a__          =  X - np.mean(__A    )
            a__          =  np.cov(reference_distribution.T    )
            try:
                 a__          =  np.linalg.inv(__A    )
            except np.linalg.LinAlgError:
                 a__          =  np.linalg.pinv(__A    )
            a__          =  np.dot(__A				,		__A    )
            a__          =  np.dot(__A				,		X_minus_mu.T    ).diagonal()

            return {"mahalanobis": mahal_dist}










"""simple docstring"""







class        _SCREAMING_SNAKE_CASE						:





							"""simple docstring"""





							def __init__(   self:     Any    ):

												'''simple docstring'''

												a__          =  {}




							def  lowercase		(   self:     Optional[int]    ):

												'''simple docstring'''

												print(self.vertex    )
												for i in self.vertex:
																	print(__A				,		''' -> '''				,		''' -> '''.join([str(__A    ) for j in self.vertex[i]]    )    )




							def  lowercase		(   self:     Union[str, Any]				,		__A:     int				,		__A:     int    ):

												'''simple docstring'''

												if from_vertex in self.vertex:
																	self.vertex[from_vertex].append(__A    )
												else:
																	# else make a new vertex
																	a__          =  [to_vertex]




							def  lowercase		(   self:     Dict    ):

												'''simple docstring'''

												a__          =  [False] * len(self.vertex    )

												# call the recursive helper function
												for i in range(len(self.vertex    )    ):
																	if not visited[i]:
																						self.dfs_recursive(__A				,		__A    )





							def  lowercase		(   self:     Optional[int]				,		__A:     int				,		__A:     list    ):

												'''simple docstring'''

												a__          =  True

												print(__A				,		end=''' '''    )

												# Recur for all the vertices that are adjacent to this node
												for i in self.vertex:
																	if not visited[i]:
																						self.dfs_recursive(__A				,		__A    )


if __name__ == "__main__":
	__a       :	Any             = Graph()
	g.add_edge(0, 1)
	g.add_edge(0, 2)
	g.add_edge(1, 2)
	g.add_edge(2, 0)
	g.add_edge(2, 3)
	g.add_edge(3, 3)

	g.print_graph()
	print('DFS:')
	g.dfs()

	# OUTPUT:
	# 0  ->  1 -> 2
	# 1  ->  2
	# 2  ->  0 -> 3
	# 3  ->  3
	# DFS:
	#  0 1 2 3


