


import itertools
from dataclasses import dataclass
from typing import Any, Callable, Dict, List, Optional, Union

import pandas as pd
import pyarrow as pa

import datasets
import datasets.config
from datasets.features.features import require_storage_cast
from datasets.table import table_cast
from datasets.utils.py_utils import Literal


snake_case							: int      =   datasets.utils.logging.get_logger(__name__)

snake_case							: List[Any]      =   ['''names''', '''prefix''']
snake_case							: List[Any]      =   ['''warn_bad_lines''', '''error_bad_lines''', '''mangle_dupe_cols''']
snake_case							: List[Any]      =   ['''encoding_errors''', '''on_bad_lines''']
snake_case							: str      =   ['''date_format''']







@dataclass
class  snake_case_     (datasets.BuilderConfig   ):
					UpperCAmelCase__      :					str					   =    ","
					UpperCAmelCase__      :					Optional[str]					   =    None
					UpperCAmelCase__      :					Optional[Union[int, List[int], str]]					   =    "infer"
					UpperCAmelCase__      :					Optional[List[str]]					   =    None
					UpperCAmelCase__      :					Optional[List[str]]					   =    None
					UpperCAmelCase__      :					Optional[Union[int, str, List[int], List[str]]]					   =    None
					UpperCAmelCase__      :					Optional[Union[List[int], List[str]]]					   =    None
					UpperCAmelCase__      :					Optional[str]					   =    None
					UpperCAmelCase__      :					bool					   =    True
					UpperCAmelCase__      :					Optional[Literal["c", "python", "pyarrow"]]					   =    None
					UpperCAmelCase__      :					Dict[Union[int, str], Callable[[Any], Any]]					   =    None
					UpperCAmelCase__      :					Optional[list]					   =    None
					UpperCAmelCase__      :					Optional[list]					   =    None
					UpperCAmelCase__      :					bool					   =    False
					UpperCAmelCase__      :					Optional[Union[int, List[int]]]					   =    None
					UpperCAmelCase__      :					Optional[int]					   =    None
					UpperCAmelCase__      :					Optional[Union[str, List[str]]]					   =    None
					UpperCAmelCase__      :					bool					   =    True
					UpperCAmelCase__      :					bool					   =    True
					UpperCAmelCase__      :					bool					   =    False
					UpperCAmelCase__      :					bool					   =    True
					UpperCAmelCase__      :					Optional[str]					   =    None
					UpperCAmelCase__      :					str					   =    "."
					UpperCAmelCase__      :					Optional[str]					   =    None
					UpperCAmelCase__      :					str					   =    '"'
					UpperCAmelCase__      :					int					   =    0
					UpperCAmelCase__      :					Optional[str]					   =    None
					UpperCAmelCase__      :					Optional[str]					   =    None
					UpperCAmelCase__      :					Optional[str]					   =    None
					UpperCAmelCase__      :					Optional[str]					   =    None
					UpperCAmelCase__      :					bool					   =    True
					UpperCAmelCase__      :					bool					   =    True
					UpperCAmelCase__      :					int					   =    0
					UpperCAmelCase__      :					bool					   =    True
					UpperCAmelCase__      :					bool					   =    False
					UpperCAmelCase__      :					Optional[str]					   =    None
					UpperCAmelCase__      :					int					   =    1_0_0_0_0
					UpperCAmelCase__      :					Optional[datasets.Features]					   =    None
					UpperCAmelCase__      :					Optional[str]					   =    "strict"
					UpperCAmelCase__      :					Literal["error", "warn", "skip"]					   =    "error"
					UpperCAmelCase__      :					Optional[str]					   =    None
					def 				lowerCamelCase__(   self     :str   )      ->					Optional[int]:
												if self.delimiter is not None:
																			a__    =  self.delimiter
												if self.column_names is not None:
																			a__    =  self.column_names



					@property
					def 				lowerCamelCase__(   self     :Tuple   )      ->					str:
												a__    =  {
												    'sep': self.sep,
												    'header': self.header,
												    'names': self.names,
												    'index_col': self.index_col,
												    'usecols': self.usecols,
												    'prefix': self.prefix,
												    'mangle_dupe_cols': self.mangle_dupe_cols,
												    'engine': self.engine,
												    'converters': self.converters,
												    'true_values': self.true_values,
												    'false_values': self.false_values,
												    'skipinitialspace': self.skipinitialspace,
												    'skiprows': self.skiprows,
												    'nrows': self.nrows,
												    'na_values': self.na_values,
												    'keep_default_na': self.keep_default_na,
												    'na_filter': self.na_filter,
												    'verbose': self.verbose,
												    'skip_blank_lines': self.skip_blank_lines,
												    'thousands': self.thousands,
												    'decimal': self.decimal,
												    'lineterminator': self.lineterminator,
												    'quotechar': self.quotechar,
												    'quoting': self.quoting,
												    'escapechar': self.escapechar,
												    'comment': self.comment,
												    'encoding': self.encoding,
												    'dialect': self.dialect,
												    'error_bad_lines': self.error_bad_lines,
												    'warn_bad_lines': self.warn_bad_lines,
												    'skipfooter': self.skipfooter,
												    'doublequote': self.doublequote,
												    'memory_map': self.memory_map,
												    'float_precision': self.float_precision,
												    'chunksize': self.chunksize,
												    'encoding_errors': self.encoding_errors,
												    'on_bad_lines': self.on_bad_lines,
												    'date_format': self.date_format,
												}

												# some kwargs must not be passed if they don't have a default value
												# some others are deprecated and we can also not pass them if they are the default value
												for pd_read_csv_parameter in _PANDAS_READ_CSV_NO_DEFAULT_PARAMETERS + _PANDAS_READ_CSV_DEPRECATED_PARAMETERS:
																			if pd_read_csv_kwargs[pd_read_csv_parameter] == getattr(CsvConfig()    ,__snake_case   ):
																										del pd_read_csv_kwargs[pd_read_csv_parameter]

        # Remove 2.0 new arguments
												if not (datasets.config.PANDAS_VERSION.major >= 2):
																			for pd_read_csv_parameter in _PANDAS_READ_CSV_NEW_2_0_0_PARAMETERS:
																										del pd_read_csv_kwargs[pd_read_csv_parameter]

        # Remove 1.3 new arguments
												if not (datasets.config.PANDAS_VERSION.major >= 1 and datasets.config.PANDAS_VERSION.minor >= 3):
																			for pd_read_csv_parameter in _PANDAS_READ_CSV_NEW_1_3_0_PARAMETERS:
																										del pd_read_csv_kwargs[pd_read_csv_parameter]

												return pd_read_csv_kwargs







class  snake_case_     (datasets.ArrowBasedBuilder   ):
					UpperCAmelCase__      :					Optional[Any]					   =    CsvConfig
					def 				lowerCamelCase__(   self     :Union[str, Any]   )      ->					List[str]:
												return datasets.DatasetInfo(features=self.config.features   )
					def 				lowerCamelCase__(   self     :str    ,__snake_case     :Tuple   )      ->					int:
												if not self.config.data_files:
																			raise ValueError(F'At least one data file must be specified, but got data_files={self.config.data_files}'   )
												a__    =  dl_manager.download_and_extract(self.config.data_files   )
												if isinstance(__snake_case    ,(str, list, tuple)   ):
																			a__    =  data_files
																			if isinstance(__snake_case    ,__snake_case   ):
																										a__    =  [files]
																			a__    =  [dl_manager.iter_files(__snake_case   ) for file in files]
																			return [datasets.SplitGenerator(name=datasets.Split.TRAIN    ,gen_kwargs={'files': files}   )]
												a__    =  []
												for split_name, files in data_files.items():
																			if isinstance(__snake_case    ,__snake_case   ):
																										a__    =  [files]
																			a__    =  [dl_manager.iter_files(__snake_case   ) for file in files]
																			splits.append(datasets.SplitGenerator(name=__snake_case    ,gen_kwargs={'files': files}   )   )
												return splits
					def 				lowerCamelCase__(   self     :int    ,__snake_case     :pa.Table   )      ->					pa.Table:
												if self.config.features is not None:
																			a__    =  self.config.features.arrow_schema
																			if all(not require_storage_cast(__snake_case   ) for feature in self.config.features.values()   ):
																										# cheaper cast
																										a__    =  pa.Table.from_arrays([pa_table[field.name] for field in schema]    ,schema=__snake_case   )
																			else:
																										# more expensive cast; allows str <-> int/float or str to Audio for example
																										a__    =  table_cast(__snake_case    ,__snake_case   )
												return pa_table



					def 				lowerCamelCase__(   self     :Tuple    ,__snake_case     :Optional[Any]   )      ->					Dict:
												a__    =  self.config.features.arrow_schema if self.config.features else None
												# dtype allows reading an int column as str
												a__    =  (
												    {
												        name: dtype.to_pandas_dtype() if not require_storage_cast(__snake_case   ) else object
												        for name, dtype, feature in zip(schema.names    ,schema.types    ,self.config.features.values()   )
												    }
												    if schema is not None
												    else None
												)
												for file_idx, file in enumerate(itertools.chain.from_iterable(__snake_case   )   ):
																			a__    =  pd.read_csv(__snake_case    ,iterator=__snake_case    ,dtype=__snake_case    ,**self.config.pd_read_csv_kwargs   )
																			try:
																										for batch_idx, df in enumerate(__snake_case   ):
																																	a__    =  pa.Table.from_pandas(__snake_case   )
																																	# Uncomment for debugging (will print the Arrow table size and elements)
																																	# logger.warning(f"pa_table: {pa_table} num rows: {pa_table.num_rows}")
																																	# logger.warning('\n'.join(str(pa_table.slice(i, 1).to_pydict()) for i in range(pa_table.num_rows)))
																																	yield (file_idx, batch_idx), self._cast_table(__snake_case   )
																			except ValueError as e:
																										logger.error(F'Failed to read file \'{file}\' with error {type(__snake_case   )}: {e}'   )
																										raise








def 							__lowercase     (				__lowerCAmelCase							:       int     ):
							a__    =  generate_pascal_triangle(__lowerCAmelCase     )
							for row_idx in range(__lowerCAmelCase     ):
														# Print left spaces
														for _ in range(num_rows - row_idx - 1     ):
																					print(end=' '     )
														# Print row values
														for col_idx in range(row_idx + 1     ):
																					if col_idx != row_idx:
																												print(triangle[row_idx][col_idx]      ,					end=' '     )
																					else:
																												print(triangle[row_idx][col_idx]      ,					end=''     )
														print()






def 							__lowercase     (				__lowerCAmelCase							:       int     ):

							if not isinstance(__lowerCAmelCase      ,					__lowerCAmelCase     ):
														raise TypeError('The input value of \'num_rows\' should be \'int\''     )

							if num_rows == 0:
														return []
							elif num_rows < 0:
														raise ValueError(
														    'The input value of \'num_rows\' should be greater than or equal to 0'     )

							a__    =  []
							for current_row_idx in range(__lowerCAmelCase     ):
														a__    =  populate_current_row(__lowerCAmelCase      ,					__lowerCAmelCase     )
														triangle.append(__lowerCAmelCase     )
							return triangle






def 							__lowercase     (				__lowerCAmelCase							:       list[list[int]]      ,					__lowerCAmelCase							:       int     ):
							a__    =  [-1] * (current_row_idx + 1)
							# first and last elements of current row are equal to 1
							a__   ,      a__    =  1, 1
							for current_col_idx in range(1      ,					__lowerCAmelCase     ):
														calculate_current_element(
														    __lowerCAmelCase      ,					__lowerCAmelCase      ,					__lowerCAmelCase      ,					__lowerCAmelCase     )
							return current_row






def 							__lowercase     (				__lowerCAmelCase							:       list[list[int]]      ,					__lowerCAmelCase							:       list[int]      ,					__lowerCAmelCase							:       int      ,					__lowerCAmelCase							:       int      ,					):
							a__    =  triangle[current_row_idx - 1][current_col_idx - 1]
							a__    =  triangle[current_row_idx - 1][current_col_idx]
							a__    =  above_to_left_elt + above_to_right_elt






def 							__lowercase     (				__lowerCAmelCase							:       int     ):

							if not isinstance(__lowerCAmelCase      ,					__lowerCAmelCase     ):
														raise TypeError('The input value of \'num_rows\' should be \'int\''     )

							if num_rows == 0:
														return []
							elif num_rows < 0:
														raise ValueError(
														    'The input value of \'num_rows\' should be greater than or equal to 0'     )

							a__    =  [[1]]

							for row_index in range(1      ,					__lowerCAmelCase     ):
														a__    =  [0] + result[-1] + [0]
														a__    =  row_index + 1
														# Calculate the number of distinct elements in a row
														a__    =  sum(divmod(__lowerCAmelCase      ,					2     )     )
														a__    =  [
														    temp_row[i - 1] + temp_row[i] for i in range(1      ,					distinct_elements + 1     )
														]
														a__    =  row_first_half[: (row_index + 1) // 2]
														row_second_half.reverse()
														a__    =  row_first_half + row_second_half
														result.append(__lowerCAmelCase     )

							return result






def 							__lowercase     (				):
							from collections.abc import Callable
							from timeit import timeit

							def benchmark_a_function(__lowerCAmelCase							:       Callable      ,					__lowerCAmelCase							:       int     ) -> None:
														a__    =  F'{func.__name__}({value})'
														a__    =  timeit(F'__main__.{call}'      ,					setup='import __main__'     )
														# print(f"{call:38} = {func(value)} -- {timing:.4f} seconds")
														print(F'{call:38} -- {timing:.4f} seconds'     )

							for value in range(1_5     ):  # (1, 7, 14):
														for func in (generate_pascal_triangle, generate_pascal_triangle_optimized):
																					benchmark_a_function(__lowerCAmelCase      ,					__lowerCAmelCase     )
														print()


if __name__ == "__main__":
						import doctest

						doctest.testmod()
						benchmark()




