
# Copyright 2023 The HuggingFace Team. All rights reserved.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
#     http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.

import torch

from accelerate import PartialState
from accelerate.utils.operations import broadcast, gather, gather_object, pad_across_processes, reduce






def      lowerCamelCase__       (       __lowerCAmelCase						:						str       ):




			"""simple docstring"""


			return (torch.arange(state.num_processes       ) + 1.0 + (state.num_processes * state.process_index)).to(state.device       )






def      lowerCamelCase__       (       __lowerCAmelCase						:						Dict       ):




			"""simple docstring"""


			lowerCAmelCase_      			=			create_tensor(__lowerCAmelCase       )
			lowerCAmelCase_      			=			gather(__lowerCAmelCase       )
			assert gathered_tensor.tolist() == list(range(1					,							state.num_processes**2 + 1       )       )






def      lowerCamelCase__       (       __lowerCAmelCase						:						Union[str, Any]       ):




			"""simple docstring"""


			lowerCAmelCase_      			=			[state.process_index]
			lowerCAmelCase_      			=			gather_object(__lowerCAmelCase       )
			assert len(__lowerCAmelCase       ) == state.num_processes, F"""{gathered_obj}, {len(__lowerCAmelCase       )} != {state.num_processes}"""
			assert gathered_obj == list(range(state.num_processes       )       ), F"""{gathered_obj} != {list(range(state.num_processes       )       )}"""






def      lowerCamelCase__       (       __lowerCAmelCase						:						int       ):




			"""simple docstring"""


			lowerCAmelCase_      			=			create_tensor(__lowerCAmelCase       )
			lowerCAmelCase_      			=			broadcast(__lowerCAmelCase       )
			assert broadcasted_tensor.shape == torch.Size([state.num_processes]       )
			assert broadcasted_tensor.tolist() == list(range(1					,							state.num_processes + 1       )       )






def      lowerCamelCase__       (       __lowerCAmelCase						:						Tuple       ):




			"""simple docstring"""


			if state.is_main_process:
						lowerCAmelCase_      			=			torch.arange(state.num_processes + 1       ).to(state.device       )
			else:
						lowerCAmelCase_      			=			torch.arange(state.num_processes       ).to(state.device       )
			lowerCAmelCase_      			=			pad_across_processes(__lowerCAmelCase       )
			assert padded_tensor.shape == torch.Size([state.num_processes + 1]       )
			if not state.is_main_process:
						assert padded_tensor.tolist() == list(range(0					,							state.num_processes       )       ) + [0]






def      lowerCamelCase__       (       __lowerCAmelCase						:						Any       ):




			"""simple docstring"""


			if state.num_processes != 2:
						return
			lowerCAmelCase_      			=			create_tensor(__lowerCAmelCase       )
			lowerCAmelCase_      			=			reduce(__lowerCAmelCase					,							"sum"       )
			lowerCAmelCase_      			=			torch.tensor([4.0, 6]       ).to(state.device       )
			assert torch.allclose(__lowerCAmelCase					,							__lowerCAmelCase       ), F"""{reduced_tensor} != {truth_tensor}"""






def      lowerCamelCase__       (       __lowerCAmelCase						:						List[Any]       ):




			"""simple docstring"""


			if state.num_processes != 2:
						return
			lowerCAmelCase_      			=			create_tensor(__lowerCAmelCase       )
			lowerCAmelCase_      			=			reduce(__lowerCAmelCase					,							"mean"       )
			lowerCAmelCase_      			=			torch.tensor([2.0, 3]       ).to(state.device       )
			assert torch.allclose(__lowerCAmelCase					,							__lowerCAmelCase       ), F"""{reduced_tensor} != {truth_tensor}"""






def      lowerCamelCase__       (       __lowerCAmelCase						:						List[Any]       ):




			"""simple docstring"""


			main()






def      lowerCamelCase__       (       ):




			"""simple docstring"""


			lowerCAmelCase_      			=			PartialState()
			state.print(F"""State: {state}"""       )
			state.print("testing gather"       )
			test_gather(__lowerCAmelCase       )
			state.print("testing gather_object"       )
			test_gather_object(__lowerCAmelCase       )
			state.print("testing broadcast"       )
			test_broadcast(__lowerCAmelCase       )
			state.print("testing pad_across_processes"       )
			test_pad_across_processes(__lowerCAmelCase       )
			state.print("testing reduce_sum"       )
			test_reduce_sum(__lowerCAmelCase       )
			state.print("testing reduce_mean"       )
			test_reduce_mean(__lowerCAmelCase       )


if __name__ == "__main__":
			main()





import itertools
import string
from collections.abc import Generator, Iterable






def      lowerCamelCase__       (       __lowerCAmelCase						:						Iterable[str]					,							__lowerCAmelCase						:						int       ):




			"""simple docstring"""


			lowerCAmelCase_      			=			iter(__lowerCAmelCase       )
			while True:
						lowerCAmelCase_      			=			tuple(itertools.islice(__lowerCAmelCase					,							__lowerCAmelCase       )       )
						if not chunk:
									return
						yield chunk






def      lowerCamelCase__       (       __lowerCAmelCase						:						str       ):




			"""simple docstring"""


			lowerCAmelCase_      			=			"".join([c.upper() for c in dirty if c in string.ascii_letters]       )
			lowerCAmelCase_      			=			""

			if len(__lowerCAmelCase       ) < 2:
						return dirty

			for i in range(len(__lowerCAmelCase       ) - 1       ):
						clean += dirty[i]

						if dirty[i] == dirty[i + 1]:
									clean += "X"

			clean += dirty[-1]

			if len(__lowerCAmelCase       ) & 1:
						clean += "X"

			return clean






def      lowerCamelCase__       (       __lowerCAmelCase						:						str       ):




			"""simple docstring"""


			lowerCAmelCase_      			=			"ABCDEFGHIKLMNOPQRSTUVWXYZ"
			# we're using a list instead of a '2d' array because it makes the math
			# for setting up the table and doing the actual encoding/decoding simpler
			lowerCAmelCase_      			=			[]

			# copy key chars into the table if they are in `alphabet` ignoring duplicates
			for char in key.upper():
						if char not in table and char in alphabet:
									table.append(__lowerCAmelCase       )

    # fill the rest of the table in with the remaining alphabet chars
			for char in alphabet:
						if char not in table:
									table.append(__lowerCAmelCase       )

			return table






def      lowerCamelCase__       (       __lowerCAmelCase						:						str					,							__lowerCAmelCase						:						str       ):




			"""simple docstring"""


			lowerCAmelCase_      			=			generate_table(__lowerCAmelCase       )
			lowerCAmelCase_      			=			prepare_input(__lowerCAmelCase       )
			lowerCAmelCase_      			=			""

			# https://en.wikipedia.org/wiki/Playfair_cipher#Description
			for chara, chara in chunker(__lowerCAmelCase					,							2       ):
						lowerCAmelCase_			,						lowerCAmelCase_      			=			divmod(table.index(__lowerCAmelCase       )					,							5       )
						lowerCAmelCase_			,						lowerCAmelCase_      			=			divmod(table.index(__lowerCAmelCase       )					,							5       )

						if rowa == rowa:
									ciphertext += table[rowa * 5 + (cola + 1) % 5]
									ciphertext += table[rowa * 5 + (cola + 1) % 5]
						elif cola == cola:
									ciphertext += table[((rowa + 1) % 5) * 5 + cola]
									ciphertext += table[((rowa + 1) % 5) * 5 + cola]
						else:  # rectangle
									ciphertext += table[rowa * 5 + cola]
									ciphertext += table[rowa * 5 + cola]

			return ciphertext






def      lowerCamelCase__       (       __lowerCAmelCase						:						str					,							__lowerCAmelCase						:						str       ):




			"""simple docstring"""


			lowerCAmelCase_      			=			generate_table(__lowerCAmelCase       )
			lowerCAmelCase_      			=			""

			# https://en.wikipedia.org/wiki/Playfair_cipher#Description
			for chara, chara in chunker(__lowerCAmelCase					,							2       ):
						lowerCAmelCase_			,						lowerCAmelCase_      			=			divmod(table.index(__lowerCAmelCase       )					,							5       )
						lowerCAmelCase_			,						lowerCAmelCase_      			=			divmod(table.index(__lowerCAmelCase       )					,							5       )

						if rowa == rowa:
									plaintext += table[rowa * 5 + (cola - 1) % 5]
									plaintext += table[rowa * 5 + (cola - 1) % 5]
						elif cola == cola:
									plaintext += table[((rowa - 1) % 5) * 5 + cola]
									plaintext += table[((rowa - 1) % 5) * 5 + cola]
						else:  # rectangle
									plaintext += table[rowa * 5 + cola]
									plaintext += table[rowa * 5 + cola]

			return plaintext



