





import json
import os
from functools import lru_cache
from typing import List, Optional, Tuple

import regex as re

from ...tokenization_utils import AddedToken, PreTrainedTokenizer
from ...utils import logging


lowercase_          =		logging.get_logger(__name__)


lowercase_          =		{"""vocab_file""": """vocab.json""", """merges_file""": """merges.txt"""}

lowercase_          =		{
    """vocab_file""": {
        """allenai/longformer-base-4096""": """https://huggingface.co/allenai/longformer-base-4096/resolve/main/vocab.json""",
        """allenai/longformer-large-4096""": (
            """https://huggingface.co/allenai/longformer-large-4096/resolve/main/vocab.json"""
        ),
        """allenai/longformer-large-4096-finetuned-triviaqa""": (
            """https://huggingface.co/allenai/longformer-large-4096-finetuned-triviaqa/resolve/main/vocab.json"""
        ),
        """allenai/longformer-base-4096-extra.pos.embd.only""": (
            """https://huggingface.co/allenai/longformer-base-4096-extra.pos.embd.only/resolve/main/vocab.json"""
        ),
        """allenai/longformer-large-4096-extra.pos.embd.only""": (
            """https://huggingface.co/allenai/longformer-large-4096-extra.pos.embd.only/resolve/main/vocab.json"""
        ),
    },
    """merges_file""": {
        """allenai/longformer-base-4096""": """https://huggingface.co/allenai/longformer-base-4096/resolve/main/merges.txt""",
        """allenai/longformer-large-4096""": (
            """https://huggingface.co/allenai/longformer-large-4096/resolve/main/merges.txt"""
        ),
        """allenai/longformer-large-4096-finetuned-triviaqa""": (
            """https://huggingface.co/allenai/longformer-large-4096-finetuned-triviaqa/resolve/main/merges.txt"""
        ),
        """allenai/longformer-base-4096-extra.pos.embd.only""": (
            """https://huggingface.co/allenai/longformer-base-4096-extra.pos.embd.only/resolve/main/merges.txt"""
        ),
        """allenai/longformer-large-4096-extra.pos.embd.only""": (
            """https://huggingface.co/allenai/longformer-large-4096-extra.pos.embd.only/resolve/main/merges.txt"""
        ),
    },
}

lowercase_          =		{
    """allenai/longformer-base-4096""": 4_096,
    """allenai/longformer-large-4096""": 4_096,
    """allenai/longformer-large-4096-finetuned-triviaqa""": 4_096,
    """allenai/longformer-base-4096-extra.pos.embd.only""": 4_096,
    """allenai/longformer-large-4096-extra.pos.embd.only""": 4_096,
}




@lru_cache()
# Copied from transformers.models.roberta.tokenization_roberta.bytes_to_unicode
def       __UpperCamelCase  ()    ->       Union[str, Any]:
  lowercase__           =  (
      list(range(ord('!'		)		,						ord('~'		) + 1		)		) + list(range(ord('¡'		)		,						ord('¬'		) + 1		)		) + list(range(ord('®'		)		,						ord('ÿ'		) + 1		)		)
  )
  lowercase__           =  bs[:]
  lowercase__           =  0
  for b in range(2**8		):
    if b not in bs:
      bs.append(_SCREAMING_SNAKE_CASE		)
      cs.append(2**8 + n		)
      n += 1
  lowercase__           =  [chr(_SCREAMING_SNAKE_CASE		) for n in cs]
  return dict(zip(_SCREAMING_SNAKE_CASE		,						_SCREAMING_SNAKE_CASE		)		)




def       __UpperCamelCase  (_SCREAMING_SNAKE_CASE		)    ->       Union[str, Any]:
  lowercase__           =  set()
  lowercase__           =  word[0]
  for char in word[1:]:
    pairs.add((prev_char, char)		)
    lowercase__           =  char
  return pairs


class     SCREAMING_SNAKE_CASE       (UpperCAmelCase				):
   _UpperCamelCase   :		str			 =	VOCAB_FILES_NAMES
   _UpperCamelCase   :		Optional[int]			 =	PRETRAINED_VOCAB_FILES_MAP
   _UpperCamelCase   :		Union[str, Any]			 =	PRETRAINED_POSITIONAL_EMBEDDINGS_SIZES
   _UpperCamelCase   :		Any			 =	['input_ids', 'attention_mask']


   def __init__(   self      :    Dict      ,					a      :    Union[str, Any]      ,					a      :    Optional[Any]      ,					a      :    List[str]="replace"      ,					a      :    Optional[int]="<s>"      ,					a      :    List[str]="</s>"      ,					a      :    List[Any]="</s>"      ,					a      :    Union[str, Any]="<s>"      ,					a      :    Any="<unk>"      ,					a      :    Optional[int]="<pad>"      ,					a      :    Optional[Any]="<mask>"      ,					a      :    Tuple=False      ,					**a      :    List[Any]      ,					)->       Optional[int]:





     """simple docstring"""







     lowercase__           =  AddedToken(a      ,					lstrip=a      ,					rstrip=a	) if isinstance(a      ,					a	) else bos_token
     lowercase__           =  AddedToken(a      ,					lstrip=a      ,					rstrip=a	) if isinstance(a      ,					a	) else eos_token
     lowercase__           =  AddedToken(a      ,					lstrip=a      ,					rstrip=a	) if isinstance(a      ,					a	) else sep_token
     lowercase__           =  AddedToken(a      ,					lstrip=a      ,					rstrip=a	) if isinstance(a      ,					a	) else cls_token
     lowercase__           =  AddedToken(a      ,					lstrip=a      ,					rstrip=a	) if isinstance(a      ,					a	) else unk_token
     lowercase__           =  AddedToken(a      ,					lstrip=a      ,					rstrip=a	) if isinstance(a      ,					a	) else pad_token

     # Mask token behave like a normal word, i.e. include the space before it
     lowercase__           =  AddedToken(a      ,					lstrip=a      ,					rstrip=a	) if isinstance(a      ,					a	) else mask_token

     super().__init__(
         errors=a      ,					bos_token=a      ,					eos_token=a      ,					unk_token=a      ,					sep_token=a      ,					cls_token=a      ,					pad_token=a      ,					mask_token=a      ,					add_prefix_space=a      ,					**a      ,					)

     with open(a      ,					encoding='utf-8'	) as vocab_handle:
       lowercase__           =  json.load(a	)
     lowercase__           =  {v: k for k, v in self.encoder.items()}
     lowercase__           =  errors  # how to handle errors in decoding
     lowercase__           =  bytes_to_unicode()
     lowercase__           =  {v: k for k, v in self.byte_encoder.items()}
     with open(a      ,					encoding='utf-8'	) as merges_handle:
       lowercase__           =  merges_handle.read().split('\n'	)[1:-1]
     lowercase__           =  [tuple(merge.split()	) for merge in bpe_merges]
     lowercase__           =  dict(zip(a      ,					range(len(a	)	)	)	)
     lowercase__           =  {}
     lowercase__           =  add_prefix_space

     # Should have added re.IGNORECASE so BPE merges can happen for capitalized versions of contractions
     lowercase__           =  re.compile(R'\'s|\'t|\'re|\'ve|\'m|\'ll|\'d| ?\p{L}+| ?\p{N}+| ?[^\s\p{L}\p{N}]+|\s+(?!\S)|\s+'	)


   @property
   def 	SCREAMING_SNAKE_CASE_							(   self      :    int	)->       Any:





     """simple docstring"""







     return len(self.encoder	)


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Dict	)->       Optional[int]:





     """simple docstring"""







     return dict(self.encoder      ,					**self.added_tokens_encoder	)


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Optional[Any]      ,					a      :    List[Any]	)->       Dict:





     """simple docstring"""







     if token in self.cache:
       return self.cache[token]
     lowercase__           =  tuple(a	)
     lowercase__           =  get_pairs(a	)

     if not pairs:
       return token

     while True:
       lowercase__           =  min(a      ,					key=lambda a	: self.bpe_ranks.get(a      ,					float('inf'	)	)	)
       if bigram not in self.bpe_ranks:
         break
       lowercase__      ,   lowercase__           =  bigram
       lowercase__           =  []
       lowercase__           =  0
       while i < len(a	):
         try:
           lowercase__           =  word.index(a      ,					a	)
         except ValueError:
           new_word.extend(word[i:]	)
           break
         else:
           new_word.extend(word[i:j]	)
           lowercase__           =  j

         if word[i] == first and i < len(a	) - 1 and word[i + 1] == second:
           new_word.append(first + second	)
           i += 2
         else:
           new_word.append(word[i]	)
           i += 1
       lowercase__           =  tuple(a	)
       lowercase__           =  new_word
       if len(a	) == 1:
         break
       else:
         lowercase__           =  get_pairs(a	)
     lowercase__           =  ' '.join(a	)
     lowercase__           =  word
     return word


   def 	SCREAMING_SNAKE_CASE_							(   self      :    List[Any]      ,					a      :    str	)->       Optional[Any]:





     """simple docstring"""







     lowercase__           =  []
     for token in re.findall(self.pat      ,					a	):
       lowercase__           =  ''.join(
           self.byte_encoder[b] for b in token.encode('utf-8'	)	)  # Maps all our bytes to unicode strings, avoiding control tokens of the BPE (spaces in our case)
       bpe_tokens.extend(bpe_token for bpe_token in self.bpe(a	).split(' '	)	)
     return bpe_tokens


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Tuple      ,					a      :    List[Any]	)->       Optional[int]:





     """simple docstring"""







     return self.encoder.get(a      ,					self.encoder.get(self.unk_token	)	)


   def 	SCREAMING_SNAKE_CASE_							(   self      :    List[str]      ,					a      :    Optional[Any]	)->       Union[str, Any]:





     """simple docstring"""







     return self.decoder.get(a	)


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Optional[int]      ,					a      :    Optional[int]	)->       Dict:





     """simple docstring"""







     lowercase__           =  ''.join(a	)
     lowercase__           =  bytearray([self.byte_decoder[c] for c in text]	).decode('utf-8'      ,					errors=self.errors	)
     return text


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Any      ,					a      :    str      ,					a      :    Optional[str] = None	)->       Tuple[str]:





     """simple docstring"""







     if not os.path.isdir(a	):
       logger.error(f"""Vocabulary path ({save_directory}) should be a directory"""	)
       return
     lowercase__           =  os.path.join(
         a      ,					(filename_prefix + '-' if filename_prefix else '') + VOCAB_FILES_NAMES['vocab_file']	)
     lowercase__           =  os.path.join(
         a      ,					(filename_prefix + '-' if filename_prefix else '') + VOCAB_FILES_NAMES['merges_file']	)

     with open(a      ,					'w'      ,					encoding='utf-8'	) as f:
       f.write(json.dumps(self.encoder      ,					indent=2      ,					sort_keys=a      ,					ensure_ascii=a	) + '\n'	)

     lowercase__           =  0
     with open(a      ,					'w'      ,					encoding='utf-8'	) as writer:
       writer.write('#version: 0.2\n'	)
       for bpe_tokens, token_index in sorted(self.bpe_ranks.items()      ,					key=lambda a	: kv[1]	):
         if index != token_index:
           logger.warning(
               f"""Saving vocabulary to {merge_file}: BPE merge indices are not consecutive."""
               ' Please check that the tokenizer is not corrupted!'	)
           lowercase__           =  token_index
         writer.write(' '.join(a	) + '\n'	)
         index += 1

     return vocab_file, merge_file


   def 	SCREAMING_SNAKE_CASE_							(   self      :    List[Any]      ,					a      :    List[int]      ,					a      :    Optional[List[int]] = None	)->       List[int]:





     """simple docstring"""







     if token_ids_a is None:
       return [self.cls_token_id] + token_ids_a + [self.sep_token_id]
     lowercase__           =  [self.cls_token_id]
     lowercase__           =  [self.sep_token_id]
     return cls + token_ids_a + sep + sep + token_ids_a + sep


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Tuple      ,					a      :    List[int]      ,					a      :    Optional[List[int]] = None      ,					a      :    bool = False	)->       List[int]:





     """simple docstring"""







     if already_has_special_tokens:
       return super().get_special_tokens_mask(
           token_ids_a=a      ,					token_ids_a=a      ,					already_has_special_tokens=a	)

     if token_ids_a is None:
       return [1] + ([0] * len(a	)) + [1]
     return [1] + ([0] * len(a	)) + [1, 1] + ([0] * len(a	)) + [1]


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Optional[int]      ,					a      :    List[int]      ,					a      :    Optional[List[int]] = None	)->       List[int]:





     """simple docstring"""







     lowercase__           =  [self.sep_token_id]
     lowercase__           =  [self.cls_token_id]

     if token_ids_a is None:
       return len(cls + token_ids_a + sep	) * [0]
     return len(cls + token_ids_a + sep + sep + token_ids_a + sep	) * [0]


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Any      ,					a      :    Dict      ,					a      :    Dict=False      ,					**a      :    Union[str, Any]	)->       Optional[int]:





     """simple docstring"""







     lowercase__           =  kwargs.pop('add_prefix_space'      ,					self.add_prefix_space	)
     if (is_split_into_words or add_prefix_space) and (len(a	) > 0 and not text[0].isspace()):
       lowercase__           =  ' ' + text
     return (text, kwargs)









from binascii import hexlify
from hashlib import shaaaa
from os import urandom

# RFC 3526 - More Modular Exponential (MODP) Diffie-Hellman groups for
# Internet Key Exchange (IKE) https://tools.ietf.org/html/rfc3526

lowercase_          =		{
    # 1536-bit
    5: {
        """prime""": int(
            """FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD1"""
            + """29024E088A67CC74020BBEA63B139B22514A08798E3404DD"""
            + """EF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245"""
            + """E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED"""
            + """EE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3D"""
            + """C2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F"""
            + """83655D23DCA3AD961C62F356208552BB9ED529077096966D"""
            + """670C354E4ABC9804F1746C08CA237327FFFFFFFFFFFFFFFF""",
            base=16,
        ),
        """generator""": 2,
    },
    # 2048-bit
    14: {
        """prime""": int(
            """FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD1"""
            + """29024E088A67CC74020BBEA63B139B22514A08798E3404DD"""
            + """EF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245"""
            + """E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED"""
            + """EE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3D"""
            + """C2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F"""
            + """83655D23DCA3AD961C62F356208552BB9ED529077096966D"""
            + """670C354E4ABC9804F1746C08CA18217C32905E462E36CE3B"""
            + """E39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9"""
            + """DE2BCBF6955817183995497CEA956AE515D2261898FA0510"""
            + """15728E5A8AACAA68FFFFFFFFFFFFFFFF""",
            base=16,
        ),
        """generator""": 2,
    },
    # 3072-bit
    15: {
        """prime""": int(
            """FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD1"""
            + """29024E088A67CC74020BBEA63B139B22514A08798E3404DD"""
            + """EF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245"""
            + """E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED"""
            + """EE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3D"""
            + """C2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F"""
            + """83655D23DCA3AD961C62F356208552BB9ED529077096966D"""
            + """670C354E4ABC9804F1746C08CA18217C32905E462E36CE3B"""
            + """E39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9"""
            + """DE2BCBF6955817183995497CEA956AE515D2261898FA0510"""
            + """15728E5A8AAAC42DAD33170D04507A33A85521ABDF1CBA64"""
            + """ECFB850458DBEF0A8AEA71575D060C7DB3970F85A6E1E4C7"""
            + """ABF5AE8CDB0933D71E8C94E04A25619DCEE3D2261AD2EE6B"""
            + """F12FFA06D98A0864D87602733EC86A64521F2B18177B200C"""
            + """BBE117577A615D6C770988C0BAD946E208E24FA074E5AB31"""
            + """43DB5BFCE0FD108E4B82D120A93AD2CAFFFFFFFFFFFFFFFF""",
            base=16,
        ),
        """generator""": 2,
    },
    # 4096-bit
    16: {
        """prime""": int(
            """FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD1"""
            + """29024E088A67CC74020BBEA63B139B22514A08798E3404DD"""
            + """EF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245"""
            + """E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED"""
            + """EE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3D"""
            + """C2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F"""
            + """83655D23DCA3AD961C62F356208552BB9ED529077096966D"""
            + """670C354E4ABC9804F1746C08CA18217C32905E462E36CE3B"""
            + """E39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9"""
            + """DE2BCBF6955817183995497CEA956AE515D2261898FA0510"""
            + """15728E5A8AAAC42DAD33170D04507A33A85521ABDF1CBA64"""
            + """ECFB850458DBEF0A8AEA71575D060C7DB3970F85A6E1E4C7"""
            + """ABF5AE8CDB0933D71E8C94E04A25619DCEE3D2261AD2EE6B"""
            + """F12FFA06D98A0864D87602733EC86A64521F2B18177B200C"""
            + """BBE117577A615D6C770988C0BAD946E208E24FA074E5AB31"""
            + """43DB5BFCE0FD108E4B82D120A92108011A723C12A787E6D7"""
            + """88719A10BDBA5B2699C327186AF4E23C1A946834B6150BDA"""
            + """2583E9CA2AD44CE8DBBBC2DB04DE8EF92E8EFC141FBECAA6"""
            + """287C59474E6BC05D99B2964FA090C3A2233BA186515BE7ED"""
            + """1F612970CEE2D7AFB81BDD762170481CD0069127D5B05AA9"""
            + """93B4EA988D8FDDC186FFB7DC90A6C08F4DF435C934063199"""
            + """FFFFFFFFFFFFFFFF""",
            base=16,
        ),
        """generator""": 2,
    },
    # 6144-bit
    17: {
        """prime""": int(
            """FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD129024E08"""
            + """8A67CC74020BBEA63B139B22514A08798E3404DDEF9519B3CD3A431B"""
            + """302B0A6DF25F14374FE1356D6D51C245E485B576625E7EC6F44C42E9"""
            + """A637ED6B0BFF5CB6F406B7EDEE386BFB5A899FA5AE9F24117C4B1FE6"""
            + """49286651ECE45B3DC2007CB8A163BF0598DA48361C55D39A69163FA8"""
            + """FD24CF5F83655D23DCA3AD961C62F356208552BB9ED529077096966D"""
            + """670C354E4ABC9804F1746C08CA18217C32905E462E36CE3BE39E772C"""
            + """180E86039B2783A2EC07A28FB5C55DF06F4C52C9DE2BCBF695581718"""
            + """3995497CEA956AE515D2261898FA051015728E5A8AAAC42DAD33170D"""
            + """04507A33A85521ABDF1CBA64ECFB850458DBEF0A8AEA71575D060C7D"""
            + """B3970F85A6E1E4C7ABF5AE8CDB0933D71E8C94E04A25619DCEE3D226"""
            + """1AD2EE6BF12FFA06D98A0864D87602733EC86A64521F2B18177B200C"""
            + """BBE117577A615D6C770988C0BAD946E208E24FA074E5AB3143DB5BFC"""
            + """E0FD108E4B82D120A92108011A723C12A787E6D788719A10BDBA5B26"""
            + """99C327186AF4E23C1A946834B6150BDA2583E9CA2AD44CE8DBBBC2DB"""
            + """04DE8EF92E8EFC141FBECAA6287C59474E6BC05D99B2964FA090C3A2"""
            + """233BA186515BE7ED1F612970CEE2D7AFB81BDD762170481CD0069127"""
            + """D5B05AA993B4EA988D8FDDC186FFB7DC90A6C08F4DF435C934028492"""
            + """36C3FAB4D27C7026C1D4DCB2602646DEC9751E763DBA37BDF8FF9406"""
            + """AD9E530EE5DB382F413001AEB06A53ED9027D831179727B0865A8918"""
            + """DA3EDBEBCF9B14ED44CE6CBACED4BB1BDB7F1447E6CC254B33205151"""
            + """2BD7AF426FB8F401378CD2BF5983CA01C64B92ECF032EA15D1721D03"""
            + """F482D7CE6E74FEF6D55E702F46980C82B5A84031900B1C9E59E7C97F"""
            + """BEC7E8F323A97A7E36CC88BE0F1D45B7FF585AC54BD407B22B4154AA"""
            + """CC8F6D7EBF48E1D814CC5ED20F8037E0A79715EEF29BE32806A1D58B"""
            + """B7C5DA76F550AA3D8A1FBFF0EB19CCB1A313D55CDA56C9EC2EF29632"""
            + """387FE8D76E3C0468043E8F663F4860EE12BF2D5B0B7474D6E694F91E"""
            + """6DCC4024FFFFFFFFFFFFFFFF""",
            base=16,
        ),
        """generator""": 2,
    },
    # 8192-bit
    18: {
        """prime""": int(
            """FFFFFFFFFFFFFFFFC90FDAA22168C234C4C6628B80DC1CD1"""
            + """29024E088A67CC74020BBEA63B139B22514A08798E3404DD"""
            + """EF9519B3CD3A431B302B0A6DF25F14374FE1356D6D51C245"""
            + """E485B576625E7EC6F44C42E9A637ED6B0BFF5CB6F406B7ED"""
            + """EE386BFB5A899FA5AE9F24117C4B1FE649286651ECE45B3D"""
            + """C2007CB8A163BF0598DA48361C55D39A69163FA8FD24CF5F"""
            + """83655D23DCA3AD961C62F356208552BB9ED529077096966D"""
            + """670C354E4ABC9804F1746C08CA18217C32905E462E36CE3B"""
            + """E39E772C180E86039B2783A2EC07A28FB5C55DF06F4C52C9"""
            + """DE2BCBF6955817183995497CEA956AE515D2261898FA0510"""
            + """15728E5A8AAAC42DAD33170D04507A33A85521ABDF1CBA64"""
            + """ECFB850458DBEF0A8AEA71575D060C7DB3970F85A6E1E4C7"""
            + """ABF5AE8CDB0933D71E8C94E04A25619DCEE3D2261AD2EE6B"""
            + """F12FFA06D98A0864D87602733EC86A64521F2B18177B200C"""
            + """BBE117577A615D6C770988C0BAD946E208E24FA074E5AB31"""
            + """43DB5BFCE0FD108E4B82D120A92108011A723C12A787E6D7"""
            + """88719A10BDBA5B2699C327186AF4E23C1A946834B6150BDA"""
            + """2583E9CA2AD44CE8DBBBC2DB04DE8EF92E8EFC141FBECAA6"""
            + """287C59474E6BC05D99B2964FA090C3A2233BA186515BE7ED"""
            + """1F612970CEE2D7AFB81BDD762170481CD0069127D5B05AA9"""
            + """93B4EA988D8FDDC186FFB7DC90A6C08F4DF435C934028492"""
            + """36C3FAB4D27C7026C1D4DCB2602646DEC9751E763DBA37BD"""
            + """F8FF9406AD9E530EE5DB382F413001AEB06A53ED9027D831"""
            + """179727B0865A8918DA3EDBEBCF9B14ED44CE6CBACED4BB1B"""
            + """DB7F1447E6CC254B332051512BD7AF426FB8F401378CD2BF"""
            + """5983CA01C64B92ECF032EA15D1721D03F482D7CE6E74FEF6"""
            + """D55E702F46980C82B5A84031900B1C9E59E7C97FBEC7E8F3"""
            + """23A97A7E36CC88BE0F1D45B7FF585AC54BD407B22B4154AA"""
            + """CC8F6D7EBF48E1D814CC5ED20F8037E0A79715EEF29BE328"""
            + """06A1D58BB7C5DA76F550AA3D8A1FBFF0EB19CCB1A313D55C"""
            + """DA56C9EC2EF29632387FE8D76E3C0468043E8F663F4860EE"""
            + """12BF2D5B0B7474D6E694F91E6DBE115974A3926F12FEE5E4"""
            + """38777CB6A932DF8CD8BEC4D073B931BA3BC832B68D9DD300"""
            + """741FA7BF8AFC47ED2576F6936BA424663AAB639C5AE4F568"""
            + """3423B4742BF1C978238F16CBE39D652DE3FDB8BEFC848AD9"""
            + """22222E04A4037C0713EB57A81A23F0C73473FC646CEA306B"""
            + """4BCBC8862F8385DDFA9D4B7FA2C087E879683303ED5BDD3A"""
            + """062B3CF5B3A278A66D2A13F83F44F82DDF310EE074AB6A36"""
            + """4597E899A0255DC164F31CC50846851DF9AB48195DED7EA1"""
            + """B1D510BD7EE74D73FAF36BC31ECFA268359046F4EB879F92"""
            + """4009438B481C6CD7889A002ED5EE382BC9190DA6FC026E47"""
            + """9558E4475677E9AA9E3050E2765694DFC81F56E880B96E71"""
            + """60C980DD98EDD3DFFFFFFFFFFFFFFFFF""",
            base=16,
        ),
        """generator""": 2,
    },
}
class     SCREAMING_SNAKE_CASE       :


   def __init__(   self      :    Optional[Any]      ,					a      :    int = 14	)->       None:





     """simple docstring"""







     if group not in primes:
       raise ValueError('Unsupported Group'	)
     lowercase__           =  primes[group]['prime']
     lowercase__           =  primes[group]['generator']

     lowercase__           =  int(hexlify(urandom(32	)	)      ,					base=16	)


   def 	SCREAMING_SNAKE_CASE_							(   self      :    List[str]	)->       str:





     """simple docstring"""







     return hex(self.__private_key	)[2:]


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Tuple	)->       str:





     """simple docstring"""







     lowercase__           =  pow(self.generator      ,					self.__private_key      ,					self.prime	)
     return hex(a	)[2:]


   def 	SCREAMING_SNAKE_CASE_							(   self      :    Tuple      ,					a      :    int	)->       bool:





     """simple docstring"""







     return (
         2 <= key <= self.prime - 2
         and pow(a      ,					(self.prime - 1) // 2      ,					self.prime	) == 1
     )


   def 	SCREAMING_SNAKE_CASE_							(   self      :    str      ,					a      :    str	)->       str:





     """simple docstring"""







     lowercase__           =  int(a      ,					base=16	)
     if not self.is_valid_public_key(a	):
       raise ValueError('Invalid public key'	)
     lowercase__           =  pow(a      ,					self.__private_key      ,					self.prime	)
     return shaaaa(str(a	).encode()	).hexdigest()


   @staticmethod
   def 	SCREAMING_SNAKE_CASE_							(   a      :    int      ,					a      :    int	)->       bool:





     """simple docstring"""







     return (
         2 <= remote_public_key_str <= prime - 2
         and pow(a      ,					(prime - 1) // 2      ,					a	) == 1
     )


   @staticmethod
   def 	SCREAMING_SNAKE_CASE_							(   a      :    str      ,					a      :    str      ,					a      :    int = 14	)->       str:





     """simple docstring"""







     lowercase__           =  int(a      ,					base=16	)
     lowercase__           =  int(a      ,					base=16	)
     lowercase__           =  primes[group]['prime']
     if not DiffieHellman.is_valid_public_key_static(a      ,					a	):
       raise ValueError('Invalid public key'	)
     lowercase__           =  pow(a      ,					a      ,					a	)
     return shaaaa(str(a	).encode()	).hexdigest()


if __name__ == "__main__":
      import doctest

      doctest.testmod()


