bases.alphabet.abstract API documentation
Description: Abstract alphabets.

# Module `bases.alphabet.abstract`

Abstract alphabets.

Expand source code

    """
        Abstract alphabets.
    """

    from abc import ABC, abstractmethod
    from typing import Any, Mapping, Optional, overload, Sequence, TypeVar, Union

    Self = TypeVar("Self", bound="Alphabet")

    class Alphabet(ABC, Sequence[str]):
        """
            Abstract superclass for alphabets with specified case sensitivity.
            It contains a mapping of digits (numbers in `range(len(self))`) to characters
            and a reverse mapping of characters to digits:

            ```py
            >>> alphabet.base16
            StringAlphabet('0123456789ABCDEF')
            >>> alphabet.base16[12]
            'C'
            >>> alphabet.base16.index("C")
            12
            ```
        """

        _case_sensitive: bool

        def __init__(self, case_sensitive: bool = True):
            self._case_sensitive = case_sensitive

        @property
        def case_sensitive(self) -> bool:
            """
                Case sensitivity of the alphabet (default: `True`).
                If set to `False`, characters will be deemed in the alphabet regardless of case.
                However, accessing characters from the alphabet will yield the case originally specified:

                ```py
                >>> alphabet.base32
                StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                               case_sensitive=False)
                >>> "a" in alphabet.base32
                True
                >>> alphabet.base32[0]
                'A'
                ```
            """
            return self._case_sensitive

        def index(self, char: str, start: int = 0, stop: Optional[int] = None) -> int:
            """
                Returns the index of a character in the alphabet.
                Raises `ValueError` if the character is not in the alphabet.
                Optionally allows a starting index (included) and stopping index (excluded).

                Example usage:

                ```py
                >>> alphabet.base32
                StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                               case_sensitive=False)
                >>> alphabet.base32.index("F")
                5
                >>> alphabet.base32[5]
                'F'
                >>> alphabet.base32.index("f") # case-insensitive
                5
                ```
            """
            # pylint: disable = arguments-renamed
            if start < 0:
                start = max(len(self) + start, 0)
            if stop is None:
                stop = start+max(len(self)-start, 0)
            elif stop < 0:
                stop += len(self)
            revdir = self.revdir
            if char not in revdir:
                raise ValueError(f"Char {repr(char)} not in alphabet.")
            idx = revdir[char]
            if not start <= idx < stop:
                raise ValueError(f"Char {repr(char)} not in alphabet[{start}:{stop}].")
            return idx

        def count(self, char: str) -> int:
            """
                Returns 1 if `char` is in the alphabet and 0 otherwise.
            """
            # pylint: disable = arguments-renamed
            return 1 if char in self else 0

        def __contains__(self, char: Any) -> bool:
            if not isinstance(char, str):
                return False
            return char in self.revdir

        @property
        @abstractmethod
        def revdir(self) -> Mapping[str, int]:
            """
                Reverse directory for the alphabet, mapping characters to their index.

                Example usage:

                ```py
                >>> alphabet.base16.revdir
                mappingproxy({'0': 0, '1': 1, '2': 2, '3': 3, '4': 4,
                              '5': 5, '6': 6, '7': 7, '8': 8, '9': 9,
                              'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15})
                ```

                For case-insensitive alphabets, this contains both cases of any cased characters:

                ```py
                >>> alphabet.base16.with_case_sensitivity(False).revdir
                mappingproxy({'0': 0, '1': 1, '2': 2, '3': 3, '4': 4,
                              '5': 5, '6': 6, '7': 7,'8': 8, '9': 9,
                              'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15,
                              'a': 10, 'b': 11, 'c': 12, 'd': 13, 'e': 14, 'f': 15})
                ```
            """
            ...

        @abstractmethod
        def with_case_sensitivity(self: Self, case_sensitive: bool) -> Self:
            """
                Returns a new alphabet with the same characters as this one but with specified case sensitivity.

                Example usage:

                ```py
                >>> alphabet.base32
                StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                               case_sensitive=False)
                >>> alphabet.base32.with_case_sensitivity(True)
                StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567')
                ```
            """
            ...

        @abstractmethod
        def upper(self) -> "Alphabet":
            """
                Returns a new alphabet with all cased characters turned to uppercase.

                Example usage:

                ```py
                >>> alphabet.base32z
                StringAlphabet('ybndrfg8ejkmcpqxot1uwisza345h769',
                               case_sensitive=False)
                >>> alphabet.base32z.upper()
                StringAlphabet('YBNDRFG8EJKMCPQXOT1UWISZA345H769',
                               case_sensitive=False)
                ```
            """
            ...

        @abstractmethod
        def lower(self) -> "Alphabet":
            """
                Returns a new alphabet with all cased characters turned to lowercase.

                Example usage:

                ```py
                >>> alphabet.base16
                StringAlphabet('0123456789ABCDEF')
                >>> alphabet.base16.lower()
                StringAlphabet('0123456789abcdef')
                ```
            """
            ...

        @abstractmethod
        def __len__(self) -> int:
            ...

        @overload
        def __getitem__(self, idx: int) -> str:
            ...

        @overload
        def __getitem__(self, idx: slice) -> "Alphabet":
            ...

        @abstractmethod
        def __getitem__(self, idx: Union[int, slice]) -> Union[str, "Alphabet"]: #type: ignore
            ...

## Classes

`class Alphabet (case_sensitive: bool = True)`

  Abstract superclass for alphabets with specified case sensitivity. It contains a mapping of digits (numbers in `range(len(self))`) to characters and a reverse mapping of characters to digits:

      >>> alphabet.base16
      StringAlphabet('0123456789ABCDEF')
      >>> alphabet.base16[12]
      'C'
      >>> alphabet.base16.index("C")
      12

  Expand source code

      class Alphabet(ABC, Sequence[str]):
          """
              Abstract superclass for alphabets with specified case sensitivity.
              It contains a mapping of digits (numbers in `range(len(self))`) to characters
              and a reverse mapping of characters to digits:

              ```py
              >>> alphabet.base16
              StringAlphabet('0123456789ABCDEF')
              >>> alphabet.base16[12]
              'C'
              >>> alphabet.base16.index("C")
              12
              ```
          """

          _case_sensitive: bool

          def __init__(self, case_sensitive: bool = True):
              self._case_sensitive = case_sensitive

          @property
          def case_sensitive(self) -> bool:
              """
                  Case sensitivity of the alphabet (default: `True`).
                  If set to `False`, characters will be deemed in the alphabet regardless of case.
                  However, accessing characters from the alphabet will yield the case originally specified:

                  ```py
                  >>> alphabet.base32
                  StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                                 case_sensitive=False)
                  >>> "a" in alphabet.base32
                  True
                  >>> alphabet.base32[0]
                  'A'
                  ```
              """
              return self._case_sensitive

          def index(self, char: str, start: int = 0, stop: Optional[int] = None) -> int:
              """
                  Returns the index of a character in the alphabet.
                  Raises `ValueError` if the character is not in the alphabet.
                  Optionally allows a starting index (included) and stopping index (excluded).

                  Example usage:

                  ```py
                  >>> alphabet.base32
                  StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                                 case_sensitive=False)
                  >>> alphabet.base32.index("F")
                  5
                  >>> alphabet.base32[5]
                  'F'
                  >>> alphabet.base32.index("f") # case-insensitive
                  5
                  ```
              """
              # pylint: disable = arguments-renamed
              if start < 0:
                  start = max(len(self) + start, 0)
              if stop is None:
                  stop = start+max(len(self)-start, 0)
              elif stop < 0:
                  stop += len(self)
              revdir = self.revdir
              if char not in revdir:
                  raise ValueError(f"Char {repr(char)} not in alphabet.")
              idx = revdir[char]
              if not start <= idx < stop:
                  raise ValueError(f"Char {repr(char)} not in alphabet[{start}:{stop}].")
              return idx

          def count(self, char: str) -> int:
              """
                  Returns 1 if `char` is in the alphabet and 0 otherwise.
              """
              # pylint: disable = arguments-renamed
              return 1 if char in self else 0

          def __contains__(self, char: Any) -> bool:
              if not isinstance(char, str):
                  return False
              return char in self.revdir

          @property
          @abstractmethod
          def revdir(self) -> Mapping[str, int]:
              """
                  Reverse directory for the alphabet, mapping characters to their index.

                  Example usage:

                  ```py
                  >>> alphabet.base16.revdir
                  mappingproxy({'0': 0, '1': 1, '2': 2, '3': 3, '4': 4,
                                '5': 5, '6': 6, '7': 7, '8': 8, '9': 9,
                                'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15})
                  ```

                  For case-insensitive alphabets, this contains both cases of any cased characters:

                  ```py
                  >>> alphabet.base16.with_case_sensitivity(False).revdir
                  mappingproxy({'0': 0, '1': 1, '2': 2, '3': 3, '4': 4,
                                '5': 5, '6': 6, '7': 7,'8': 8, '9': 9,
                                'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15,
                                'a': 10, 'b': 11, 'c': 12, 'd': 13, 'e': 14, 'f': 15})
                  ```
              """
              ...

          @abstractmethod
          def with_case_sensitivity(self: Self, case_sensitive: bool) -> Self:
              """
                  Returns a new alphabet with the same characters as this one but with specified case sensitivity.

                  Example usage:

                  ```py
                  >>> alphabet.base32
                  StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                                 case_sensitive=False)
                  >>> alphabet.base32.with_case_sensitivity(True)
                  StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567')
                  ```
              """
              ...

          @abstractmethod
          def upper(self) -> "Alphabet":
              """
                  Returns a new alphabet with all cased characters turned to uppercase.

                  Example usage:

                  ```py
                  >>> alphabet.base32z
                  StringAlphabet('ybndrfg8ejkmcpqxot1uwisza345h769',
                                 case_sensitive=False)
                  >>> alphabet.base32z.upper()
                  StringAlphabet('YBNDRFG8EJKMCPQXOT1UWISZA345H769',
                                 case_sensitive=False)
                  ```
              """
              ...

          @abstractmethod
          def lower(self) -> "Alphabet":
              """
                  Returns a new alphabet with all cased characters turned to lowercase.

                  Example usage:

                  ```py
                  >>> alphabet.base16
                  StringAlphabet('0123456789ABCDEF')
                  >>> alphabet.base16.lower()
                  StringAlphabet('0123456789abcdef')
                  ```
              """
              ...

          @abstractmethod
          def __len__(self) -> int:
              ...

          @overload
          def __getitem__(self, idx: int) -> str:
              ...

          @overload
          def __getitem__(self, idx: slice) -> "Alphabet":
              ...

          @abstractmethod
          def __getitem__(self, idx: Union[int, slice]) -> Union[str, "Alphabet"]: #type: ignore
              ...

  ### Ancestors

  - abc.ABC
  - collections.abc.Sequence
  - collections.abc.Reversible
  - collections.abc.Collection
  - collections.abc.Sized
  - collections.abc.Iterable
  - collections.abc.Container
  - typing.Generic

  ### Subclasses

  - RangeAlphabet
  - StringAlphabet

  ### Instance variables

  `var case_sensitive : bool`

    Case sensitivity of the alphabet (default: `True`). If set to `False`, characters will be deemed in the alphabet regardless of case. However, accessing characters from the alphabet will yield the case originally specified:

        >>> alphabet.base32
        StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                       case_sensitive=False)
        >>> "a" in alphabet.base32
        True
        >>> alphabet.base32[0]
        'A'

    Expand source code

        @property
        def case_sensitive(self) -> bool:
            """
                Case sensitivity of the alphabet (default: `True`).
                If set to `False`, characters will be deemed in the alphabet regardless of case.
                However, accessing characters from the alphabet will yield the case originally specified:

                ```py
                >>> alphabet.base32
                StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                               case_sensitive=False)
                >>> "a" in alphabet.base32
                True
                >>> alphabet.base32[0]
                'A'
                ```
            """
            return self._case_sensitive

  `var revdir : Mapping[str, int]`

    Reverse directory for the alphabet, mapping characters to their index.

    Example usage:

        >>> alphabet.base16.revdir
        mappingproxy({'0': 0, '1': 1, '2': 2, '3': 3, '4': 4,
                      '5': 5, '6': 6, '7': 7, '8': 8, '9': 9,
                      'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15})

    For case-insensitive alphabets, this contains both cases of any cased characters:

        >>> alphabet.base16.with_case_sensitivity(False).revdir
        mappingproxy({'0': 0, '1': 1, '2': 2, '3': 3, '4': 4,
                      '5': 5, '6': 6, '7': 7,'8': 8, '9': 9,
                      'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15,
                      'a': 10, 'b': 11, 'c': 12, 'd': 13, 'e': 14, 'f': 15})

    Expand source code

        @property
        @abstractmethod
        def revdir(self) -> Mapping[str, int]:
            """
                Reverse directory for the alphabet, mapping characters to their index.

                Example usage:

                ```py
                >>> alphabet.base16.revdir
                mappingproxy({'0': 0, '1': 1, '2': 2, '3': 3, '4': 4,
                              '5': 5, '6': 6, '7': 7, '8': 8, '9': 9,
                              'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15})
                ```

                For case-insensitive alphabets, this contains both cases of any cased characters:

                ```py
                >>> alphabet.base16.with_case_sensitivity(False).revdir
                mappingproxy({'0': 0, '1': 1, '2': 2, '3': 3, '4': 4,
                              '5': 5, '6': 6, '7': 7,'8': 8, '9': 9,
                              'A': 10, 'B': 11, 'C': 12, 'D': 13, 'E': 14, 'F': 15,
                              'a': 10, 'b': 11, 'c': 12, 'd': 13, 'e': 14, 'f': 15})
                ```
            """
            ...

  ### Methods

  `def count(self, char: str) ‑> int`

    Returns 1 if `char` is in the alphabet and 0 otherwise.

    Expand source code

        def count(self, char: str) -> int:
            """
                Returns 1 if `char` is in the alphabet and 0 otherwise.
            """
            # pylint: disable = arguments-renamed
            return 1 if char in self else 0

  `def index(self, char: str, start: int = 0, stop: Optional[int] = None) ‑> int`

    Returns the index of a character in the alphabet. Raises `ValueError` if the character is not in the alphabet. Optionally allows a starting index (included) and stopping index (excluded).

    Example usage:

        >>> alphabet.base32
        StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                       case_sensitive=False)
        >>> alphabet.base32.index("F")
        5
        >>> alphabet.base32[5]
        'F'
        >>> alphabet.base32.index("f") # case-insensitive
        5

    Expand source code

        def index(self, char: str, start: int = 0, stop: Optional[int] = None) -> int:
            """
                Returns the index of a character in the alphabet.
                Raises `ValueError` if the character is not in the alphabet.
                Optionally allows a starting index (included) and stopping index (excluded).

                Example usage:

                ```py
                >>> alphabet.base32
                StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                               case_sensitive=False)
                >>> alphabet.base32.index("F")
                5
                >>> alphabet.base32[5]
                'F'
                >>> alphabet.base32.index("f") # case-insensitive
                5
                ```
            """
            # pylint: disable = arguments-renamed
            if start < 0:
                start = max(len(self) + start, 0)
            if stop is None:
                stop = start+max(len(self)-start, 0)
            elif stop < 0:
                stop += len(self)
            revdir = self.revdir
            if char not in revdir:
                raise ValueError(f"Char {repr(char)} not in alphabet.")
            idx = revdir[char]
            if not start <= idx < stop:
                raise ValueError(f"Char {repr(char)} not in alphabet[{start}:{stop}].")
            return idx

  `def lower(self) ‑> Alphabet`

    Returns a new alphabet with all cased characters turned to lowercase.

    Example usage:

        >>> alphabet.base16
        StringAlphabet('0123456789ABCDEF')
        >>> alphabet.base16.lower()
        StringAlphabet('0123456789abcdef')

    Expand source code

        @abstractmethod
        def lower(self) -> "Alphabet":
            """
                Returns a new alphabet with all cased characters turned to lowercase.

                Example usage:

                ```py
                >>> alphabet.base16
                StringAlphabet('0123456789ABCDEF')
                >>> alphabet.base16.lower()
                StringAlphabet('0123456789abcdef')
                ```
            """
            ...

  `def upper(self) ‑> Alphabet`

    Returns a new alphabet with all cased characters turned to uppercase.

    Example usage:

        >>> alphabet.base32z
        StringAlphabet('ybndrfg8ejkmcpqxot1uwisza345h769',
                       case_sensitive=False)
        >>> alphabet.base32z.upper()
        StringAlphabet('YBNDRFG8EJKMCPQXOT1UWISZA345H769',
                       case_sensitive=False)

    Expand source code

        @abstractmethod
        def upper(self) -> "Alphabet":
            """
                Returns a new alphabet with all cased characters turned to uppercase.

                Example usage:

                ```py
                >>> alphabet.base32z
                StringAlphabet('ybndrfg8ejkmcpqxot1uwisza345h769',
                               case_sensitive=False)
                >>> alphabet.base32z.upper()
                StringAlphabet('YBNDRFG8EJKMCPQXOT1UWISZA345H769',
                               case_sensitive=False)
                ```
            """
            ...

  `def with_case_sensitivity(self: ~Self, case_sensitive: bool) ‑> ~Self`

    Returns a new alphabet with the same characters as this one but with specified case sensitivity.

    Example usage:

        >>> alphabet.base32
        StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                       case_sensitive=False)
        >>> alphabet.base32.with_case_sensitivity(True)
        StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567')

    Expand source code

        @abstractmethod
        def with_case_sensitivity(self: Self, case_sensitive: bool) -> Self:
            """
                Returns a new alphabet with the same characters as this one but with specified case sensitivity.

                Example usage:

                ```py
                >>> alphabet.base32
                StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567',
                               case_sensitive=False)
                >>> alphabet.base32.with_case_sensitivity(True)
                StringAlphabet('ABCDEFGHIJKLMNOPQRSTUVWXYZ234567')
                ```
            """
            ...