


from __future__ import annotations

lowerCAmelCase           =		tuple[int, int, int]
lowerCAmelCase           =		tuple[str, str, str]


# used alphabet --------------------------
# from string.ascii_uppercase
lowerCAmelCase           =		"ABCDEFGHIJKLMNOPQRSTUVWXYZ"

# -------------------------- default selection --------------------------
# rotors --------------------------
lowerCAmelCase           =		"EGZWVONAHDCLFQMSIPJBYUKXTR"
lowerCAmelCase           =		"FOBHMDKEXQNRAULPGSJVTYICZW"
lowerCAmelCase           =		"ZJXESIUQLHAVRMDOYGTNFWPBKC"
# reflector --------------------------
lowerCAmelCase           =		{
    "A": "N",
    "N": "A",
    "B": "O",
    "O": "B",
    "C": "P",
    "P": "C",
    "D": "Q",
    "Q": "D",
    "E": "R",
    "R": "E",
    "F": "S",
    "S": "F",
    "G": "T",
    "T": "G",
    "H": "U",
    "U": "H",
    "I": "V",
    "V": "I",
    "J": "W",
    "W": "J",
    "K": "X",
    "X": "K",
    "L": "Y",
    "Y": "L",
    "M": "Z",
    "Z": "M",
}

# -------------------------- extra rotors --------------------------
lowerCAmelCase           =		"RMDJXFUWGISLHVTCQNKYPBEZOA"
lowerCAmelCase           =		"SGLCPQWZHKXAREONTFBVIYJUDM"
lowerCAmelCase           =		"HVSICLTYKQUBXDWAJZOMFGPREN"
lowerCAmelCase           =		"RZWQHFMVDBKICJLNTUXAGYPSOE"
lowerCAmelCase           =		"LFKIJODBEGAMQPXVUHYSTCZRWN"
lowerCAmelCase           =		"KOAEGVDHXPQZMLFTYWJNBRCIUS"







def        _lowerCamelCase(	lowercase__   , lowercase__   , lowercase__	)						->	Any:

		'''simple docstring'''







		if (unique_rotsel := len(set(__lowerCamelCase	)	)) < 3:
				__lowercase=			F'Please use 3 unique rotors (not {unique_rotsel})'
				raise Exception(__lowerCamelCase	)

		# Checks if rotor positions are valid
		__lowercase=			rotpos
		if not 0 < rotorposa <= len(__lowerCamelCase	):
				__lowercase=			F'First rotor position is not within range of 1..26 ({rotorposa}'
				raise ValueError(__lowerCamelCase	)
		if not 0 < rotorposa <= len(__lowerCamelCase	):
				__lowercase=			F'Second rotor position is not within range of 1..26 ({rotorposa})'
				raise ValueError(__lowerCamelCase	)
		if not 0 < rotorposa <= len(__lowerCamelCase	):
				__lowercase=			F'Third rotor position is not within range of 1..26 ({rotorposa})'
				raise ValueError(__lowerCamelCase	)

		# Validates string and returns dict
		__lowercase=			_plugboard(__lowerCamelCase	)

		return rotpos, rotsel, pbdict







def        _lowerCamelCase(	lowercase__	)						->	Optional[Any]:

		'''simple docstring'''







		if not isinstance(__lowerCamelCase   , __lowerCamelCase	):
				__lowercase=			F'Plugboard setting isn\'t type string ({type(__lowerCamelCase	)})'
				raise TypeError(__lowerCamelCase	)
		elif len(__lowerCamelCase	) % 2 != 0:
				__lowercase=			F'Odd number of symbols ({len(__lowerCamelCase	)})'
				raise Exception(__lowerCamelCase	)
		elif pbstring == "":
				return {}

		pbstring.replace(' '   , ''	)

		# Checks if all characters are unique
		__lowercase=			set()
		for i in pbstring:
				if i not in abc:
						__lowercase=			F'\'{i}\' not in list of symbols'
						raise Exception(__lowerCamelCase	)
				elif i in tmppbl:
						__lowercase=			F'Duplicate symbol ({i})'
						raise Exception(__lowerCamelCase	)
				else:
						tmppbl.add(__lowerCamelCase	)
		del tmppbl

		# Created the dictionary
		__lowercase=			{}
		for j in range(0   , len(__lowerCamelCase	) - 1   , 2	):
				__lowercase=			pbstring[j + 1]
				__lowercase=			pbstring[j]

		return pb







def        _lowerCamelCase(	lowercase__   , lowercase__   , lowercase__ = (rotora, rotora, rotora)   , lowercase__ = ""   , )						->	List[Any]:

		'''simple docstring'''







		__lowercase=			text.upper()
		__lowercase=			_validator(
		    __lowerCamelCase   , __lowerCamelCase   , plugb.upper()	)

		__lowercase=			rotor_position
		__lowercase=			rotor_selection
		rotorposa -= 1
		rotorposa -= 1
		rotorposa -= 1

		__lowercase=			[]

		# encryption/decryption process --------------------------
		for symbol in text:
				if symbol in abc:
						# 1st plugboard --------------------------
						if symbol in plugboard:
								__lowercase=			plugboard[symbol]

						# rotor ra --------------------------
						__lowercase=			abc.index(__lowerCamelCase	) + rotorposa
						__lowercase=			rotora[index % len(__lowerCamelCase	)]

						# rotor rb --------------------------
						__lowercase=			abc.index(__lowerCamelCase	) + rotorposa
						__lowercase=			rotora[index % len(__lowerCamelCase	)]

						# rotor rc --------------------------
						__lowercase=			abc.index(__lowerCamelCase	) + rotorposa
						__lowercase=			rotora[index % len(__lowerCamelCase	)]

						# reflector --------------------------
						# this is the reason you don't need another machine to decipher

						__lowercase=			reflector[symbol]

						# 2nd rotors
						__lowercase=			abc[rotora.index(__lowerCamelCase	) - rotorposa]
						__lowercase=			abc[rotora.index(__lowerCamelCase	) - rotorposa]
						__lowercase=			abc[rotora.index(__lowerCamelCase	) - rotorposa]

						# 2nd plugboard
						if symbol in plugboard:
								__lowercase=			plugboard[symbol]

						# moves/resets rotor positions
						rotorposa += 1
						if rotorposa >= len(__lowerCamelCase	):
								__lowercase=			0
								rotorposa += 1
						if rotorposa >= len(__lowerCamelCase	):
								__lowercase=			0
								rotorposa += 1
						if rotorposa >= len(__lowerCamelCase	):
								__lowercase=			0

        # else:
        #    pass
        #    Error could be also raised
        #    raise ValueError(
        #       'Invalid symbol('+repr(symbol)+')')
				result.append(__lowerCamelCase	)

		return "".join(__lowerCamelCase	)


if __name__ == "__main__":
	lowerCAmelCase           =		"This is my Python script that emulates the Enigma machine from WWII."
	lowerCAmelCase           =		(1, 1, 1)
	lowerCAmelCase           =		"pictures"
	lowerCAmelCase           =		(rotora, rotora, rotora)
	lowerCAmelCase           =		enigma(message, rotor_pos, rotor_sel, pb)

	print('''Encrypted message:''', en)
	print('''Decrypted message:''', enigma(en, rotor_pos, rotor_sel, pb))











"""simple docstring"""






def      snake_case__   (		):
			"""simple docstring"""
			return [list(range(1000 - i							,		-1000 - i							,		-1	)	) for i in range(1000	)]


_lowercase : str      						=						generate_large_matrix()
_lowercase : str      						=						(
    [[4, 3, 2, -1], [3, 2, 1, -1], [1, 1, -1, -2], [-1, -1, -2, -3]],
    [[3, 2], [1, 0]],
    [[7, 7, 6]],
    [[7, 7, 6], [-1, -2, -3]],
    grid,
)






def      snake_case__   (		__lowerCamelCase				:    list[list[int]]	):
			"""simple docstring"""
			assert all(row == sorted(__lowerCamelCase							,		reverse=__lowerCamelCase	) for row in grid	)
			assert all(list(__lowerCamelCase	) == sorted(__lowerCamelCase							,		reverse=__lowerCamelCase	) for col in zip(*__lowerCamelCase	)	)






def      snake_case__   (		__lowerCamelCase				:    list[int]	):
			"""simple docstring"""
			lowerCamelCase__		:		int			=0
			lowerCamelCase__		:		Optional[int]			=len(__lowerCamelCase	) - 1

			# Edge cases such as no values or all numbers are negative.
			if not array or array[0] < 0:
						return 0

			while right + 1 > left:
						lowerCamelCase__		:		List[str]			=(left + right) // 2
						lowerCamelCase__		:		Union[str, Any]			=array[mid]

						# Num must be negative and the index must be greater than or equal to 0.
						if num < 0 and array[mid - 1] >= 0:
									return mid

						if num >= 0:
									lowerCamelCase__		:		Union[str, Any]			=mid + 1
						else:
									lowerCamelCase__		:		Dict			=mid - 1
    # No negative numbers so return the last index of the array + 1 which is the length.
			return len(__lowerCamelCase	)






def      snake_case__   (		__lowerCamelCase				:    list[list[int]]	):
			"""simple docstring"""
			lowerCamelCase__		:		Union[str, Any]			=0
			lowerCamelCase__		:		str			=len(grid[0]	)

			for i in range(len(__lowerCamelCase	)	):
						lowerCamelCase__		:		Any			=find_negative_index(grid[i][:bound]	)
						total += bound
			return (len(__lowerCamelCase	) * len(grid[0]	)) - total






def      snake_case__   (		__lowerCamelCase				:    list[list[int]]	):
			"""simple docstring"""
			return len([number for row in grid for number in row if number < 0]	)






def      snake_case__   (		__lowerCamelCase				:    list[list[int]]	):
			"""simple docstring"""
			lowerCamelCase__		:		Tuple			=0
			for row in grid:
						for i, number in enumerate(__lowerCamelCase	):
									if number < 0:
												total += len(__lowerCamelCase	) - i
												break
			return total






def      snake_case__   (		):
			"""simple docstring"""
			from timeit import timeit

			print('''Running benchmarks'''	)
			lowerCamelCase__		:		List[str]			=(
			    '''from __main__ import count_negatives_binary_search, '''
			    '''count_negatives_brute_force, count_negatives_brute_force_with_break, grid'''
			)
			for func in (
			    "count_negatives_binary_search",  # took 0.7727 seconds
			    "count_negatives_brute_force_with_break",  # took 4.6505 seconds
			    "count_negatives_brute_force",  # took 12.8160 seconds
			):
						lowerCamelCase__		:		Union[str, Any]			=timeit(f'''{func}(grid=grid)'''							,		setup=__lowerCamelCase							,		number=500	)
						print(f'''{func}() took {time:0.4f} seconds'''	)


if __name__ == "__main__":
		import doctest

		doctest.testmod()
		benchmark()




