


'''simple docstring'''
import sys
from dataclasses import dataclass
from typing import TYPE_CHECKING, Dict, List, Optional, Tuple, 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


if TYPE_CHECKING:
     import sqlitea

     import sqlalchemy


lowerCAmelCase__  =     datasets.utils.logging.get_logger(__name__)







@dataclass
class 					_A						(						datasets.BuilderConfig							):



   '''simple docstring'''






   _lowercase    						= None
   _lowercase    						= None
   _lowercase    						= None
   _lowercase    						= True
   _lowercase    						= None
   _lowercase    						= None
   _lowercase    						= None
   _lowercase    						= 1_0000
   _lowercase    						= None




   def   __lowerCAmelCase						(	self	:					List[Any]						)->	Any:



          if self.sql is None:
                 raise ValueError("""sql must be specified"""						)
          if self.con is None:
                 raise ValueError("""con must be specified"""						)




   def   __lowerCAmelCase						(	self	:					int					, lowerCamelCase	:					dict					, lowerCamelCase	:					Optional[datasets.Features] = None					, )->	str:
          snake_case__					:	str          =					config_kwargs.copy()
          # We need to stringify the Selectable object to make its hash deterministic

          # The process of stringifying is explained here: http://docs.sqlalchemy.org/en/latest/faq/sqlexpressions.html
          snake_case__					:	Any          =					config_kwargs["""sql"""]
          if not isinstance(lowercase__					, lowercase__						):
                 if datasets.config.SQLALCHEMY_AVAILABLE and "sqlalchemy" in sys.modules:
                        import sqlalchemy

                        if isinstance(lowercase__					, sqlalchemy.sql.Selectable						):
                               snake_case__					:	Tuple          =					sqlalchemy.create_engine(config_kwargs["""con"""].split("""://"""						)[0] + """://"""						)
                               snake_case__					:	Optional[Any]          =					str(sql.compile(dialect=engine.dialect						)						)
                               snake_case__					:	Optional[int]          =					sql_str
                        else:
                               raise TypeError(
                                   F"""Supported types for 'sql' are string and sqlalchemy.sql.Selectable but got {type(lowercase__						)}: {sql}"""						)
                 else:
                        raise TypeError(
                            F"""Supported types for 'sql' are string and sqlalchemy.sql.Selectable but got {type(lowercase__						)}: {sql}"""						)
          snake_case__					:	Any          =					config_kwargs["""con"""]
          if not isinstance(lowercase__					, lowercase__						):
                 snake_case__					:	Optional[int]          =					id(lowercase__						)
                 logger.info(
                     F"""SQL connection 'con' of type {type(lowercase__						)} couldn't be hashed properly. To enable hashing, specify 'con' as URI string instead."""						)

          return super().create_config_id(lowercase__					, custom_features=lowercase__						)




   @property
   def   __lowerCAmelCase						(	self	:					str						)->	Any:
          snake_case__					:	Dict          =					{
              """index_col""": self.index_col,
              """columns""": self.columns,
              """params""": self.params,
              """coerce_float""": self.coerce_float,
              """parse_dates""": self.parse_dates,
          }
          return pd_read_sql_kwargs







class 					_A						(						datasets.ArrowBasedBuilder							):



   '''simple docstring'''






   _lowercase    						= SqlConfig




   def   __lowerCAmelCase						(	self	:					List[Any]						)->	Dict:
          return datasets.DatasetInfo(features=self.config.features						)




   def   __lowerCAmelCase						(	self	:					int					, lowerCamelCase	:					int						)->	Tuple:
          return [datasets.SplitGenerator(name=datasets.Split.TRAIN					, gen_kwargs={}						)]




   def   __lowerCAmelCase						(	self	:					str					, lowerCamelCase	:					pa.Table						)->	pa.Table:



          if self.config.features is not None:
                 snake_case__					:	int          =					self.config.features.arrow_schema
                 if all(not require_storage_cast(lowercase__						) for feature in self.config.features.values()						):
                        # cheaper cast
                        snake_case__					:	str          =					pa.Table.from_arrays([pa_table[field.name] for field in schema]					, schema=lowercase__						)
                 else:
                        # more expensive cast; allows str <-> int/float or str to Audio for example
                        snake_case__					:	Optional[int]          =					table_cast(lowercase__					, lowercase__						)
          return pa_table




   def   __lowerCAmelCase						(	self	:					Optional[int]						)->	int:
          snake_case__					:	Optional[int]          =					self.config.chunksize
          snake_case__					:	Dict          =					pd.read_sql(
              self.config.sql					, self.config.con					, chunksize=lowercase__					, **self.config.pd_read_sql_kwargs						)
          snake_case__					:	List[str]          =					[sql_reader] if chunksize is None else sql_reader
          for chunk_idx, df in enumerate(lowercase__						):
                 snake_case__					:	str          =					pa.Table.from_pandas(lowercase__						)
                 yield chunk_idx, self._cast_table(lowercase__						)







'''simple docstring'''







from collections import namedtuple

_lowerCamelCase    =  namedtuple('from_to', 'from_ to')

_lowerCamelCase    =  {
    'millimeter': 'mm',
    'centimeter': 'cm',
    'meter': 'm',
    'kilometer': 'km',
    'inch': 'in',
    'inche': 'in',  # Trailing 's' has been stripped off
    'feet': 'ft',
    'foot': 'ft',
    'yard': 'yd',
    'mile': 'mi',
}

_lowerCamelCase    =  {
    'mm': from_to(0.001, 1_0_0_0),
    'cm': from_to(0.01, 1_0_0),
    'm': from_to(1, 1),
    'km': from_to(1_0_0_0, 0.001),
    'in': from_to(0.0254, 39.3701),
    'ft': from_to(0.3048, 3.2_8084),
    'yd': from_to(0.9144, 1.0_9361),
    'mi': from_to(1609.34, 0.0_0062_1371),
}






def 					_SCREAMING_SNAKE_CASE		(						snake_case_							,       snake_case_							,       snake_case_	):
	_lowercase							=     from_type.lower().rstrip("""s"""	)
	_lowercase							=     TYPE_CONVERSION.get(snake_case_							,       snake_case_	)
	_lowercase							=     to_type.lower().rstrip("""s"""	)
	_lowercase							=     TYPE_CONVERSION.get(snake_case_							,       snake_case_	)
	if new_from not in METRIC_CONVERSION:
		_lowercase							=     (
		    F"""Invalid 'from_type' value: {from_type!r}.\n"""
		    F"""Conversion abbreviations are: {", ".join(snake_case_	)}"""
		)
		raise ValueError(snake_case_	)
	if new_to not in METRIC_CONVERSION:
		_lowercase							=     (
		    F"""Invalid 'to_type' value: {to_type!r}.\n"""
		    F"""Conversion abbreviations are: {", ".join(snake_case_	)}"""
		)
		raise ValueError(snake_case_	)
	return value * METRIC_CONVERSION[new_from].from_ * METRIC_CONVERSION[new_to].to


if __name__ == "__main__":
							import doctest

							doctest.testmod()




