




'''simple docstring'''


#
# Sort large text files in a minimum amount of memory
#
import argparse
import os

class 			A    :
							lowercase_							=				'block_{0}.dat'







							def __init__(  self       :  str							,			lowerCAmelCase_       :  Optional[int]					)			->							List[Any]:


														"""simple docstring"""


														_a	     =				filename
														_a	     =				[]







							def    __lowerCAmelCase			(  self       :  str							,			lowerCAmelCase_       :  Optional[int]							,			lowerCAmelCase_       :  List[str]					)			->							int:


														"""simple docstring"""


														_a	     =				self.BLOCK_FILENAME_FORMAT.format(lowerCAmelCase_					)
														with open(lowerCAmelCase_							,			'''w'''					) as file:
																					file.write(lowerCAmelCase_					)
														self.block_filenames.append(lowerCAmelCase_					)







							def    __lowerCAmelCase			(  self       :  Optional[Any]					)			->							Union[str, Any]:


														"""simple docstring"""


														return self.block_filenames







							def    __lowerCAmelCase			(  self       :  Union[str, Any]							,			lowerCAmelCase_       :  Optional[Any]							,			lowerCAmelCase_       :  Tuple=None					)			->							Optional[int]:


														"""simple docstring"""


														_a	     =				0
														with open(self.filename					) as file:
																					while True:
																												_a	     =				file.readlines(lowerCAmelCase_					)

																												if lines == []:
																																			break

																												if sort_key is None:
																																			lines.sort()
																												else:
																																			lines.sort(key=lowerCAmelCase_					)

																												self.write_block(''''''.join(lowerCAmelCase_					)							,			lowerCAmelCase_					)
																												i += 1







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


														"""simple docstring"""


														map(os.remove							,			self.block_filenames					)



class 			A    :







							def    __lowerCAmelCase			(  self       :  str							,			lowerCAmelCase_       :  Optional[int]					)			->							Tuple:


														"""simple docstring"""


														_a	     =				-1
														_a	     =				None

														for i in range(len(lowerCAmelCase_					)					):
																					if min_str is None or choices[i] < min_str:
																												_a	     =				i

														return min_index



class 			A    :







							def __init__(  self       :  int							,			lowerCAmelCase_       :  Any					)			->							List[str]:


														"""simple docstring"""


														_a	     =				files
														_a	     =				set()
														_a	     =				len(lowerCAmelCase_					)
														_a	     =				{i: None for i in range(self.num_buffers					)}







							def    __lowerCAmelCase			(  self       :  int					)			->							List[str]:


														"""simple docstring"""


														return {
														    i: self.buffers[i] for i in range(self.num_buffers					) if i not in self.empty
														}







							def    __lowerCAmelCase			(  self       :  str					)			->							int:


														"""simple docstring"""


														for i in range(self.num_buffers					):
																					if self.buffers[i] is None and i not in self.empty:
																												_a	     =				self.files[i].readline()

																												if self.buffers[i] == "":
																																			self.empty.add(lowerCAmelCase_					)
																																			self.files[i].close()

														if len(self.empty					) == self.num_buffers:
																					return False

														return True







							def    __lowerCAmelCase			(  self       :  int							,			lowerCAmelCase_       :  Any					)			->							str:


														"""simple docstring"""


														_a	     =				self.buffers[index]
														_a	     =				None

														return value



class 			A    :







							def __init__(  self       :  str							,			lowerCAmelCase_       :  Optional[int]					)			->							Tuple:


														"""simple docstring"""


														_a	     =				merge_strategy







							def    __lowerCAmelCase			(  self       :  Dict							,			lowerCAmelCase_       :  Union[str, Any]							,			lowerCAmelCase_       :  List[str]							,			lowerCAmelCase_       :  int					)			->							Dict:


														"""simple docstring"""


														_a	     =				FilesArray(self.get_file_handles(lowerCAmelCase_							,			lowerCAmelCase_					)					)
														with open(lowerCAmelCase_							,			'''w'''							,			lowerCAmelCase_					) as outfile:
																					while buffers.refresh():
																												_a	     =				self.merge_strategy.select(buffers.get_dict()					)
																												outfile.write(buffers.unshift(lowerCAmelCase_					)					)







							def    __lowerCAmelCase			(  self       :  Tuple							,			lowerCAmelCase_       :  Union[str, Any]							,			lowerCAmelCase_       :  List[Any]					)			->							Optional[int]:


														"""simple docstring"""


														_a	     =				{}

														for i in range(len(lowerCAmelCase_					)					):
																					_a	     =				open(filenames[i]							,			'''r'''							,			lowerCAmelCase_					)  # noqa: UP015

														return files



class 			A    :







							def __init__(  self       :  str							,			lowerCAmelCase_       :  Optional[Any]					)			->							str:


														"""simple docstring"""


														_a	     =				block_size







							def    __lowerCAmelCase			(  self       :  Dict							,			lowerCAmelCase_       :  Optional[Any]							,			lowerCAmelCase_       :  List[str]=None					)			->							Optional[Any]:


														"""simple docstring"""


														_a	     =				self.get_number_blocks(lowerCAmelCase_							,			self.block_size					)
														_a	     =				FileSplitter(lowerCAmelCase_					)
														splitter.split(self.block_size							,			lowerCAmelCase_					)

														_a	     =				FileMerger(NWayMerge()					)
														_a	     =				self.block_size / (num_blocks + 1)
														merger.merge(splitter.get_block_filenames()							,			filename + '''.out'''							,			lowerCAmelCase_					)

														splitter.cleanup()







							def    __lowerCAmelCase			(  self       :  str							,			lowerCAmelCase_       :  int							,			lowerCAmelCase_       :  List[Any]					)			->							Optional[int]:


														"""simple docstring"""


														return (os.stat(lowerCAmelCase_					).st_size / block_size) + 1



def 		snake_case_    (UpperCamelCase       :  str      ):





							'''simple docstring'''


							if string[-1].lower() == "k":
														return int(string[:-1]      ) * 1024
							elif string[-1].lower() == "m":
														return int(string[:-1]      ) * 1024 * 1024
							elif string[-1].lower() == "g":
														return int(string[:-1]      ) * 1024 * 1024 * 1024
							else:
														return int(UpperCamelCase      )
def 		snake_case_    ():





							'''simple docstring'''


							_a	     =				argparse.ArgumentParser()
							parser.add_argument(
							    '''-m''' ,						'''--mem''' ,						help='''amount of memory to use for sorting''' ,						default='''100M'''      )
							parser.add_argument(
							    '''filename''' ,						metavar='''<filename>''' ,						nargs=1 ,						help='''name of file to sort'''      )
							_a	     =				parser.parse_args()

							_a	     =				ExternalSort(parse_memory(args.mem      )      )
							sorter.sort(args.filename[0]      )


if __name__ == "__main__":
				main()







'''simple docstring'''


from __future__ import annotations
def 		snake_case_    (UpperCamelCase       :  int      ):





							'''simple docstring'''


							_a	     =				[0] * max_one

							for i in range(0 ,						UpperCamelCase      ):
														_a	     =				i

							for i in range(2 ,						UpperCamelCase      ):
														if totients[i] == i:
																					for j in range(UpperCamelCase ,						UpperCamelCase ,						UpperCamelCase      ):
																												totients[j] -= totients[j] // i

							return totients
def 		snake_case_    (UpperCamelCase       :  int ,						UpperCamelCase       :  int      ):





							'''simple docstring'''


							return sorted(str(UpperCamelCase      )      ) == sorted(str(UpperCamelCase      )      )
def 		snake_case_    (UpperCamelCase       :  int = 1000_0000      ):





							'''simple docstring'''


							_a	     =				1  # i
							_a	     =				0  # φ(i)
							_a	     =				get_totients(max_n + 1      )

							for i in range(2 ,						max_n + 1      ):
														_a	     =				totients[i]

														if i * min_denominator < min_numerator * t and has_same_digits(UpperCamelCase ,						UpperCamelCase      ):
																					_a	     =				i
																					_a	     =				t

							return min_numerator


if __name__ == "__main__":
				print(F'''{solution() = }''')

