





from typing import List, Optional, Union

from ...image_utils import ImageInput
from ...processing_utils import ProcessorMixin
from ...tokenization_utils_base import BatchEncoding, PaddingStrategy, PreTokenizedInput, TextInput, TruncationStrategy
from ...utils import TensorType






class        _a(    __A    ):
		lowerCamelCase__     :int   				=		['image_processor', 'tokenizer']
		lowerCamelCase__     :Dict   				=		'BlipImageProcessor'
		lowerCamelCase__     :List[Any]   				=		'AutoTokenizer'







		def __init__(    self ,						__snake_case ,						__snake_case				)      ->      Union[str, Any]:


							'''simple docstring'''

							_snake_case       :					List[str]				       =   False
							super().__init__(__snake_case ,						__snake_case				)
							_snake_case       :					Dict				       =   self.image_processor







		def __call__(    self ,						__snake_case = None ,						__snake_case = None ,						__snake_case = True ,						__snake_case = False ,						__snake_case = None ,						__snake_case = None ,						__snake_case = 0 ,						__snake_case = None ,						__snake_case = None ,						__snake_case = False ,						__snake_case = False ,						__snake_case = False ,						__snake_case = False ,						__snake_case = False ,						__snake_case = True ,						__snake_case = None ,						**__snake_case ,						)      ->      BatchEncoding:


							'''simple docstring'''

							if images is None and text is None:
												raise ValueError("You have to specify either images or text."				)

							# Get only text
							if images is None:
												_snake_case       :					str				       =   self.tokenizer
												_snake_case       :					List[str]				       =   self.tokenizer(
												    text=__snake_case ,						add_special_tokens=__snake_case ,						padding=__snake_case ,						truncation=__snake_case ,						max_length=__snake_case ,						stride=__snake_case ,						pad_to_multiple_of=__snake_case ,						return_attention_mask=__snake_case ,						return_overflowing_tokens=__snake_case ,						return_special_tokens_mask=__snake_case ,						return_offsets_mapping=__snake_case ,						return_token_type_ids=__snake_case ,						return_length=__snake_case ,						verbose=__snake_case ,						return_tensors=__snake_case ,						**__snake_case ,						)
												return text_encoding

							# add pixel_values
							_snake_case       :					int				       =   self.image_processor(__snake_case ,						return_tensors=__snake_case				)

							if text is not None:
												_snake_case       :					int				       =   self.tokenizer(
												    text=__snake_case ,						add_special_tokens=__snake_case ,						padding=__snake_case ,						truncation=__snake_case ,						max_length=__snake_case ,						stride=__snake_case ,						pad_to_multiple_of=__snake_case ,						return_attention_mask=__snake_case ,						return_overflowing_tokens=__snake_case ,						return_special_tokens_mask=__snake_case ,						return_offsets_mapping=__snake_case ,						return_token_type_ids=__snake_case ,						return_length=__snake_case ,						verbose=__snake_case ,						return_tensors=__snake_case ,						**__snake_case ,						)
							else:
												_snake_case       :					Tuple				       =   None

							if text_encoding is not None:
												encoding_image_processor.update(__snake_case				)

							return encoding_image_processor







		def        lowercase       (    self ,						*__snake_case ,						**__snake_case				)      ->      Optional[Any]:


							'''simple docstring'''

							return self.tokenizer.batch_decode(*__snake_case ,						**__snake_case				)







		def        lowercase       (    self ,						*__snake_case ,						**__snake_case				)      ->      str:


							'''simple docstring'''

							return self.tokenizer.decode(*__snake_case ,						**__snake_case				)







		@property
		# Copied from transformers.models.blip.processing_blip.BlipProcessor.model_input_names
		def        lowercase       (    self				)      ->      str:


							'''simple docstring'''

							_snake_case       :					int				       =   self.tokenizer.model_input_names
							_snake_case       :					Any				       =   self.image_processor.model_input_names
							return list(dict.fromkeys(tokenizer_input_names + image_processor_input_names				)				)






from math import factorial

__lowerCAmelCase :dict[str, int]     =    {str(digit): factorial(digit) for digit in range(10)}







def    A				(							UpperCAmelCase				):
					if not isinstance(UpperCAmelCase  ,  UpperCAmelCase				):
										raise TypeError("Parameter number must be int"				)

					if number < 0:
										raise ValueError("Parameter number must be greater than or equal to 0"				)

					# Converts number in string to iterate on its digits and adds its factorial.
					return sum(DIGIT_FACTORIAL[digit] for digit in str(UpperCAmelCase				)				)







def    A				(							UpperCAmelCase = 60  ,  UpperCAmelCase = 1_000_000				):

					if not isinstance(UpperCAmelCase  ,  UpperCAmelCase				) or not isinstance(UpperCAmelCase  ,  UpperCAmelCase				):
										raise TypeError("Parameters chain_length and number_limit must be int"				)

					if chain_length <= 0 or number_limit <= 0:
										raise ValueError(
										    "Parameters chain_length and number_limit must be greater than 0"				)

					# the counter for the chains with the exact desired length
					_snake_case       :					Optional[int]				       =   0
					# the cached sizes of the previous chains
					_snake_case       :					dict[int, int]				       =   {}

					for start_chain_element in range(1  ,  UpperCAmelCase				):
										# The temporary set will contain the elements of the chain
										_snake_case       :					Union[str, Any]				       =   set()
										_snake_case       :					Tuple				       =   0

										# Stop computing the chain when you find a cached size, a repeating item or the
										# length is greater then the desired one.
										_snake_case       :					str				       =   start_chain_element
										while (
										    chain_element not in chain_sets_lengths
										    and chain_element not in chain_set
										    and chain_set_length <= chain_length
										):
															chain_set.add(UpperCAmelCase				)
															chain_set_length += 1
															_snake_case       :					Optional[Any]				       =   digit_factorial_sum(UpperCAmelCase				)

										if chain_element in chain_sets_lengths:
															chain_set_length += chain_sets_lengths[chain_element]

										_snake_case       :					List[Any]				       =   chain_set_length

										# If chain contains the exact amount of elements increase the counter
										if chain_set_length == chain_length:
															chains_counter += 1

					return chains_counter


if __name__ == "__main__":
							import doctest

							doctest.testmod()
							print(F'''{solution()}''')