
import json
import os
import tempfile
from unittest.mock import patch

import torch
from torch.utils.data import DataLoader, TensorDataset

from accelerate import DistributedType, infer_auto_device_map, init_empty_weights
from accelerate.accelerator import Accelerator
from accelerate.state import GradientState, PartialState
from accelerate.test_utils import require_bnb, require_multi_gpu, slow
from accelerate.test_utils.testing import AccelerateTestCase, require_cuda
from accelerate.utils import patch_environment



def   __SCREAMING_SNAKE_CASE (		)		-> str:
		SCREAMING_SNAKE_CASE_					:	Dict		  =			torch.nn.Linear(2 ,    4 )
		SCREAMING_SNAKE_CASE_					:	int		  =			torch.optim.AdamW(model.parameters() ,    lr=1.0 )
		SCREAMING_SNAKE_CASE_					:	Dict		  =			torch.optim.lr_scheduler.OneCycleLR(SCREAMING_SNAKE_CASE_ ,    max_lr=0.01 ,    steps_per_epoch=2 ,    epochs=1 )
		SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			DataLoader(TensorDataset(torch.tensor([1, 2, 3] ) ) )
		SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			DataLoader(TensorDataset(torch.tensor([4, 5, 6] ) ) )

		return model, optimizer, scheduler, train_dl, valid_dl



def   __SCREAMING_SNAKE_CASE (		SCREAMING_SNAKE_CASE )		-> Optional[Any]:
		return (model.weight.abs().sum() + model.bias.abs().sum()).item()



def   __SCREAMING_SNAKE_CASE (		SCREAMING_SNAKE_CASE )		-> List[str]:
		SCREAMING_SNAKE_CASE_					:	Optional[Any]		  =			torch.nn.Linear(*tuple(model.weight.T.shape ) ).state_dict()
		model.load_state_dict(SCREAMING_SNAKE_CASE_ )

class 							snake_case_ (				lowerCAmelCase    ):





			@require_cuda
			def 						__A						(		self      ):
					SCREAMING_SNAKE_CASE_					:	List[Any]		  =			Accelerator()
					assert PartialState._shared_state["_cpu"] is False
					assert PartialState._shared_state["device"].type == "cuda"
					with self.assertRaises(_lowercase      ):
							SCREAMING_SNAKE_CASE_					:	Optional[Any]		  =			Accelerator(cpu=_lowercase      )





			def 						__A						(		self      ):
					SCREAMING_SNAKE_CASE_					:	List[str]		  =			Accelerator()
					SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			GradientState()
					assert state.num_steps == 1
					SCREAMING_SNAKE_CASE_					:	Dict		  =			4
					assert state.num_steps == 4

					assert state.sync_gradients is True
					SCREAMING_SNAKE_CASE_					:	List[str]		  =			False
					assert state.sync_gradients is False
					GradientState._reset_state()





			def 						__A						(		self      ):
					SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			Accelerator()
					SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			create_components()

					(
					    (
					    SCREAMING_SNAKE_CASE_       
					)  ,      (
					    SCREAMING_SNAKE_CASE_       
					)  ,      (
					    SCREAMING_SNAKE_CASE_       
					)  ,      (
					    SCREAMING_SNAKE_CASE_       
					)  ,      (
					    SCREAMING_SNAKE_CASE_       
					)  ,             
					)					:	Union[str, Any]		  =			accelerator.prepare(_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      )

					self.assertTrue(prepared_model in accelerator._models      )
					self.assertTrue(prepared_optimizer in accelerator._optimizers      )
					self.assertTrue(prepared_scheduler in accelerator._schedulers      )
					self.assertTrue(prepared_train_dl in accelerator._dataloaders      )
					self.assertTrue(prepared_valid_dl in accelerator._dataloaders      )





			def 						__A						(		self      ):
					SCREAMING_SNAKE_CASE_					:	Any		  =			Accelerator()
					SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_					:	List[Any]		  =			create_components()
					accelerator.prepare(_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      )
					accelerator.free_memory()

					self.assertTrue(len(accelerator._models      ) == 0      )
					self.assertTrue(len(accelerator._optimizers      ) == 0      )
					self.assertTrue(len(accelerator._schedulers      ) == 0      )
					self.assertTrue(len(accelerator._dataloaders      ) == 0      )





			def 						__A						(		self      ):
					PartialState._reset_state()

					# Mock torch.cuda.set_device to avoid an exception as the device doesn't exist
					def noop(*__lowerCAmelCase      ,						**__lowerCAmelCase      ):
							pass

					with patch('torch.cuda.set_device'      ,						_lowercase      ), patch_environment(ACCELERATE_TORCH_DEVICE='cuda:64'      ):
							SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			Accelerator()
							self.assertEqual(str(accelerator.state.device      )      ,						'cuda:64'      )





			def 						__A						(		self      ):
					SCREAMING_SNAKE_CASE_					:	Union[str, Any]		  =			Accelerator()
					SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			create_components()
					accelerator.prepare(_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      )

					SCREAMING_SNAKE_CASE_					:	Dict		  =			get_signature(_lowercase      )

					with tempfile.TemporaryDirectory() as tmpdirname:
							accelerator.save_state(_lowercase      )

							# make sure random weights don't match
							load_random_weights(_lowercase      )
							self.assertTrue(abs(model_signature - get_signature(_lowercase      )      ) > 1e-3      )

							# make sure loaded weights match
							accelerator.load_state(_lowercase      )
							self.assertTrue(abs(model_signature - get_signature(_lowercase      )      ) < 1e-3      )





			def 						__A						(		self      ):
					SCREAMING_SNAKE_CASE_					:	List[str]		  =			Accelerator()
					SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_					:	Optional[Any]		  =			create_components()
					accelerator.prepare(_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      )

					SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			get_signature(_lowercase      )

					# saving hook
					def save_config(__lowerCAmelCase      ,						__lowerCAmelCase      ,						__lowerCAmelCase      ):
							SCREAMING_SNAKE_CASE_					:	str		  =			{'class_name': models[0].__class__.__name__}

							with open(os.path.join(_lowercase      ,						'data.json'      )      ,						'w'      ) as f:
									json.dump(_lowercase      ,						_lowercase      )

        # loading hook
					def load_config(__lowerCAmelCase      ,						__lowerCAmelCase      ):
							with open(os.path.join(_lowercase      ,						'data.json'      )      ,						'r'      ) as f:
									SCREAMING_SNAKE_CASE_					:	Any		  =			json.load(_lowercase      )

							SCREAMING_SNAKE_CASE_					:	str		  =			config['class_name']

					SCREAMING_SNAKE_CASE_					:	Dict		  =			accelerator.register_save_state_pre_hook(_lowercase      )
					SCREAMING_SNAKE_CASE_					:	Dict		  =			accelerator.register_load_state_pre_hook(_lowercase      )

					with tempfile.TemporaryDirectory() as tmpdirname:
							accelerator.save_state(_lowercase      )

							# make sure random weights don't match with hooks
							load_random_weights(_lowercase      )
							self.assertTrue(abs(model_signature - get_signature(_lowercase      )      ) > 1e-3      )

							# random class name to verify correct one is loaded
							SCREAMING_SNAKE_CASE_					:	List[str]		  =			'random'

							# make sure loaded weights match with hooks
							accelerator.load_state(_lowercase      )
							self.assertTrue(abs(model_signature - get_signature(_lowercase      )      ) < 1e-3      )

							# mode.class_name is loaded from config
							self.assertTrue(model.class_name == model.__class__.__name__      )

					# remove hooks
					save_hook.remove()
					load_hook.remove()

					with tempfile.TemporaryDirectory() as tmpdirname:
							accelerator.save_state(_lowercase      )

							# make sure random weights don't match with hooks removed
							load_random_weights(_lowercase      )
							self.assertTrue(abs(model_signature - get_signature(_lowercase      )      ) > 1e-3      )

							# random class name to verify correct one is loaded
							SCREAMING_SNAKE_CASE_					:	List[Any]		  =			'random'

							# make sure loaded weights match with hooks removed
							accelerator.load_state(_lowercase      )
							self.assertTrue(abs(model_signature - get_signature(_lowercase      )      ) < 1e-3      )

							# mode.class_name is NOT loaded from config
							self.assertTrue(model.class_name != model.__class__.__name__      )





			def 						__A						(		self      ):
					SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			Accelerator()
					SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			create_components()
					SCREAMING_SNAKE_CASE_					:	List[str]		  =			None

					# This should work
					SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_					:	str		  =			accelerator.prepare(
					    _lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      )
					self.assertTrue(dummy_obj is None      )





			def 						__A						(		self      ):
					SCREAMING_SNAKE_CASE_					:	Tuple		  =			Accelerator()
					SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			create_components()
					SCREAMING_SNAKE_CASE_					:	Dict		  =			[1, 2, 3]

					# This should work
					SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_  ,      SCREAMING_SNAKE_CASE_					:	str		  =			accelerator.prepare(
					    _lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      ,						_lowercase      )
					self.assertEqual(
					    getattr(_lowercase      ,						'_is_accelerate_prepared'      ,						_lowercase      )      ,						_lowercase      ,						'Dummy object should have `_is_accelerate_prepared` set to `True`'      ,						)
					self.assertEqual(
					    getattr(_lowercase      ,						'_is_accelerate_prepared'      ,						_lowercase      )      ,						_lowercase      ,						'Model is missing `_is_accelerator_prepared` or is set to `False`'      ,						)
					self.assertEqual(
					    getattr(_lowercase      ,						'_is_accelerate_prepared'      ,						_lowercase      )      ,						_lowercase      ,						'Optimizer is missing `_is_accelerator_prepared` or is set to `False`'      ,						)
					self.assertEqual(
					    getattr(_lowercase      ,						'_is_accelerate_prepared'      ,						_lowercase      )      ,						_lowercase      ,						'Scheduler is missing `_is_accelerator_prepared` or is set to `False`'      ,						)
					self.assertEqual(
					    getattr(_lowercase      ,						'_is_accelerate_prepared'      ,						_lowercase      )      ,						_lowercase      ,						'Train Dataloader is missing `_is_accelerator_prepared` or is set to `False`'      ,						)
					self.assertEqual(
					    getattr(_lowercase      ,						'_is_accelerate_prepared'      ,						_lowercase      )      ,						_lowercase      ,						'Valid Dataloader is missing `_is_accelerator_prepared` or is set to `False`'      ,						)





			@slow
			@require_bnb
			def 						__A						(		self      ):
					from transformers import AutoModelForCausalLM

					SCREAMING_SNAKE_CASE_					:	Optional[Any]		  =			AutoModelForCausalLM.from_pretrained(
					    'EleutherAI/gpt-neo-125m'      ,						load_in_abit=_lowercase      ,						device_map={'': 0}      ,						)
					SCREAMING_SNAKE_CASE_					:	str		  =			Accelerator()

					# This should work
					SCREAMING_SNAKE_CASE_					:	Dict		  =			accelerator.prepare(_lowercase      )





			@slow
			@require_bnb
			def 						__A						(		self      ):
					from transformers import AutoModelForCausalLM

					SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			Accelerator()

					with init_empty_weights():
							SCREAMING_SNAKE_CASE_					:	int		  =			AutoModelForCausalLM.from_pretrained(
							    'EleutherAI/gpt-neo-125m'      ,						)
							model.tie_weights()
							SCREAMING_SNAKE_CASE_					:	Tuple		  =			infer_auto_device_map(_lowercase      )
							SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			'cpu'

					SCREAMING_SNAKE_CASE_					:	int		  =			AutoModelForCausalLM.from_pretrained(
					    'EleutherAI/gpt-neo-125m'      ,						device_map=_lowercase      ,						load_in_abit=_lowercase      ,						llm_inta_enable_fpaa_cpu_offload=_lowercase      )

					# This should not work and get value error
					with self.assertRaises(_lowercase      ):
							SCREAMING_SNAKE_CASE_					:	Optional[int]		  =			accelerator.prepare(_lowercase      )





			@slow
			@require_bnb
			@require_multi_gpu
			def 						__A						(		self      ):
					from transformers import AutoModelForCausalLM

					SCREAMING_SNAKE_CASE_					:	Union[str, Any]		  =			{'distributed_type': DistributedType.MULTI_GPU}

					with init_empty_weights():
							SCREAMING_SNAKE_CASE_					:	Optional[Any]		  =			AutoModelForCausalLM.from_pretrained(
							    'EleutherAI/gpt-neo-125m'      ,						)
							model.tie_weights()
							SCREAMING_SNAKE_CASE_					:	Union[str, Any]		  =			infer_auto_device_map(_lowercase      )
							SCREAMING_SNAKE_CASE_					:	List[Any]		  =			1

					SCREAMING_SNAKE_CASE_					:	Dict		  =			AutoModelForCausalLM.from_pretrained(
					    'EleutherAI/gpt-neo-125m'      ,						load_in_abit=_lowercase      ,						device_map=_lowercase      ,						)
					SCREAMING_SNAKE_CASE_					:	List[str]		  =			Accelerator()

					# This should not work and get value error
					with self.assertRaises(_lowercase      ):
							SCREAMING_SNAKE_CASE_					:	Any		  =			accelerator.prepare(_lowercase      )

					PartialState._reset_state()





			@slow
			@require_bnb
			@require_multi_gpu
			def 						__A						(		self      ):
					from transformers import AutoModelForCausalLM

					with init_empty_weights():
							SCREAMING_SNAKE_CASE_					:	List[str]		  =			AutoModelForCausalLM.from_pretrained(
							    'EleutherAI/gpt-neo-125m'      ,						)
							SCREAMING_SNAKE_CASE_					:	List[str]		  =			infer_auto_device_map(_lowercase      )
							SCREAMING_SNAKE_CASE_					:	List[Any]		  =			1

					SCREAMING_SNAKE_CASE_					:	str		  =			AutoModelForCausalLM.from_pretrained(
					    'EleutherAI/gpt-neo-125m'      ,						load_in_abit=_lowercase      ,						device_map=_lowercase      ,						)
					SCREAMING_SNAKE_CASE_					:	Any		  =			Accelerator()

					# This should work
					SCREAMING_SNAKE_CASE_					:	int		  =			accelerator.prepare(_lowercase      )






			@require_cuda
			def 						__A						(		self      ):
					SCREAMING_SNAKE_CASE_					:	Any		  =			torch.nn.Linear(10      ,						10      )
					SCREAMING_SNAKE_CASE_					:	Optional[Any]		  =			torch.optim.SGD(model.parameters()      ,						lr=0.01      )
					SCREAMING_SNAKE_CASE_					:	Union[str, Any]		  =			Accelerator(cpu=_lowercase      )
					SCREAMING_SNAKE_CASE_					:	Optional[Any]		  =			accelerator.prepare(_lowercase      )









from typing import Any






class 						__magic_name__					:






     def __init__(				self		,						_lowercase	)->     List[str]:
         UpperCamelCase_			  =						data
         UpperCamelCase_			  =						None






     def __repr__(				self	)->     str:
         return F"Node({self.data})"






class 						__magic_name__					:






     def __init__(				self	)->     Optional[Any]:
         UpperCamelCase_			  =						None






     def __iter__(				self	)->     Any:
         UpperCamelCase_			  =						self.head
         while node:
             yield node.data
             UpperCamelCase_			  =						node.next






     def __len__(				self	)->     int:
         return sum(1 for _ in self	)






     def __repr__(				self	)->     str:
         return "->".join([str(_lowercase	) for item in self]	)






     def __getitem__(				self		,						_lowercase	)->     Any:
         if not 0 <= index < len(self	):
             raise ValueError("list index out of range."	)
         for i, node in enumerate(self	):
             if i == index:
                 return node
         return None






     def __setitem__(				self		,						_lowercase		,						_lowercase	)->     None:
         if not 0 <= index < len(self	):
             raise ValueError("list index out of range."	)
         UpperCamelCase_			  =						self.head
         for _ in range(_lowercase	):
             UpperCamelCase_			  =						current.next
         UpperCamelCase_			  =						data






     def 	UpperCAmelCase_				(				self		,						_lowercase	)->     None:
         self.insert_nth(len(self	)		,						_lowercase	)






     def 	UpperCAmelCase_				(				self		,						_lowercase	)->     None:
         self.insert_nth(0		,						_lowercase	)






     def 	UpperCAmelCase_				(				self		,						_lowercase		,						_lowercase	)->     None:
         if not 0 <= index <= len(self	):
             raise IndexError("list index out of range"	)
         UpperCamelCase_			  =						Node(_lowercase	)
         if self.head is None:
             UpperCamelCase_			  =						new_node
         elif index == 0:
             UpperCamelCase_			  =						self.head  # link new_node to head
             UpperCamelCase_			  =						new_node
         else:
             UpperCamelCase_			  =						self.head
             for _ in range(index - 1	):
                 UpperCamelCase_			  =						temp.next
             UpperCamelCase_			  =						temp.next
             UpperCamelCase_			  =						new_node






     def 	UpperCAmelCase_				(				self	)->     None:  # print every node data
         print(self	)






     def 	UpperCAmelCase_				(				self	)->     Any:
         return self.delete_nth(0	)






     def 	UpperCAmelCase_				(				self	)->     Any:  # delete from tail
         return self.delete_nth(len(self	) - 1	)






     def 	UpperCAmelCase_				(				self		,						_lowercase = 0	)->     Any:
         if not 0 <= index <= len(self	) - 1:  # test if index is valid
             raise IndexError("List index out of range."	)
         UpperCamelCase_			  =						self.head  # default first node
         if index == 0:
             UpperCamelCase_			  =						self.head.next
         else:
             UpperCamelCase_			  =						self.head
             for _ in range(index - 1	):
                 UpperCamelCase_			  =						temp.next
             UpperCamelCase_			  =						temp.next
             UpperCamelCase_			  =						temp.next.next
         return delete_node.data






     def 	UpperCAmelCase_				(				self	)->     bool:
         return self.head is None






     def 	UpperCAmelCase_				(				self	)->     None:
         UpperCamelCase_			  =						None
         UpperCamelCase_			  =						self.head

         while current:
             # Store the current node's next node.
             UpperCamelCase_			  =						current.next
             # Make the current node's next point backwards
             UpperCamelCase_			  =						prev
             # Make the previous node be the current node
             UpperCamelCase_			  =						current
             # Make the current node the next node (to progress iteration)
             UpperCamelCase_			  =						next_node
         # Return prev in order to put the head at the end
         UpperCamelCase_			  =						prev




def 			lowerCAmelCase(      )->						None:



    """simple docstring"""






    UpperCamelCase_			  =						LinkedList()
    assert linked_list.is_empty() is True
    assert str(SCREAMING_SNAKE_CASE_			) == ""

    try:
        linked_list.delete_head()
        raise AssertionError  # This should not happen.
    except IndexError:
        assert True  # This should happen.

    try:
        linked_list.delete_tail()
        raise AssertionError  # This should not happen.
    except IndexError:
        assert True  # This should happen.

    for i in range(1_0			):
        assert len(SCREAMING_SNAKE_CASE_			) == i
        linked_list.insert_nth(SCREAMING_SNAKE_CASE_			,						i + 1			)
    assert str(SCREAMING_SNAKE_CASE_			) == "->".join(str(SCREAMING_SNAKE_CASE_			) for i in range(1			,						1_1			)			)

    linked_list.insert_head(0			)
    linked_list.insert_tail(1_1			)
    assert str(SCREAMING_SNAKE_CASE_			) == "->".join(str(SCREAMING_SNAKE_CASE_			) for i in range(0			,						1_2			)			)

    assert linked_list.delete_head() == 0
    assert linked_list.delete_nth(9			) == 1_0
    assert linked_list.delete_tail() == 1_1
    assert len(SCREAMING_SNAKE_CASE_			) == 9
    assert str(SCREAMING_SNAKE_CASE_			) == "->".join(str(SCREAMING_SNAKE_CASE_			) for i in range(1			,						1_0			)			)

    assert all(linked_list[i] == i + 1 for i in range(0			,						9			)			) is True

    for i in range(0			,						9			):
        UpperCamelCase_			  =						-i
    assert all(linked_list[i] == -i for i in range(0			,						9			)			) is True

    linked_list.reverse()
    assert str(SCREAMING_SNAKE_CASE_			) == "->".join(str(SCREAMING_SNAKE_CASE_			) for i in range(-8			,						1			)			)




def 			lowerCAmelCase(      )->						None:



    """simple docstring"""






    UpperCamelCase_			  =						[
        -9,
        1_0_0,
        Node(7_7_3_4_5_1_1_2			),
        "dlrow olleH",
        7,
        5_5_5_5,
        0,
        -192.5_5555,
        "Hello, world!",
        77.9,
        Node(1_0			),
        None,
        None,
        12.20,
    ]
    UpperCamelCase_			  =						LinkedList()

    for i in test_input:
        linked_list.insert_tail(SCREAMING_SNAKE_CASE_			)

    # Check if it's empty or not
    assert linked_list.is_empty() is False
    assert (
        str(SCREAMING_SNAKE_CASE_			) == "-9->100->Node(77345112)->dlrow olleH->7->5555->0->"
        "-192.55555->Hello, world!->77.9->Node(10)->None->None->12.2"
    )

    # Delete the head
    UpperCamelCase_			  =						linked_list.delete_head()
    assert result == -9
    assert (
        str(SCREAMING_SNAKE_CASE_			) == "100->Node(77345112)->dlrow olleH->7->5555->0->-192.55555->"
        "Hello, world!->77.9->Node(10)->None->None->12.2"
    )

    # Delete the tail
    UpperCamelCase_			  =						linked_list.delete_tail()
    assert result == 12.2
    assert (
        str(SCREAMING_SNAKE_CASE_			) == "100->Node(77345112)->dlrow olleH->7->5555->0->-192.55555->"
        "Hello, world!->77.9->Node(10)->None->None"
    )

    # Delete a node in specific location in linked list
    UpperCamelCase_			  =						linked_list.delete_nth(1_0			)
    assert result is None
    assert (
        str(SCREAMING_SNAKE_CASE_			) == "100->Node(77345112)->dlrow olleH->7->5555->0->-192.55555->"
        "Hello, world!->77.9->Node(10)->None"
    )

    # Add a Node instance to its head
    linked_list.insert_head(Node("Hello again, world!"			)			)
    assert (
        str(SCREAMING_SNAKE_CASE_			)
        == "Node(Hello again, world!)->100->Node(77345112)->dlrow olleH->"
        "7->5555->0->-192.55555->Hello, world!->77.9->Node(10)->None"
    )

    # Add None to its tail
    linked_list.insert_tail(SCREAMING_SNAKE_CASE_			)
    assert (
        str(SCREAMING_SNAKE_CASE_			)
        == "Node(Hello again, world!)->100->Node(77345112)->dlrow olleH->"
        "7->5555->0->-192.55555->Hello, world!->77.9->Node(10)->None->None"
    )

    # Reverse the linked list
    linked_list.reverse()
    assert (
        str(SCREAMING_SNAKE_CASE_			)
        == "None->None->Node(10)->77.9->Hello, world!->-192.55555->0->5555->"
        "7->dlrow olleH->Node(77345112)->100->Node(Hello again, world!)"
    )




def 			lowerCAmelCase(      )->						List[Any]:



    """simple docstring"""






    from doctest import testmod

    testmod()

    UpperCamelCase_			  =						LinkedList()
    linked_list.insert_head(input("Inserting 1st at head "			).strip()			)
    linked_list.insert_head(input("Inserting 2nd at head "			).strip()			)
    print("\nPrint list:"			)
    linked_list.print_list()
    linked_list.insert_tail(input("\nInserting 1st at tail "			).strip()			)
    linked_list.insert_tail(input("Inserting 2nd at tail "			).strip()			)
    print("\nPrint list:"			)
    linked_list.print_list()
    print("\nDelete head"			)
    linked_list.delete_head()
    print("Delete tail"			)
    linked_list.delete_tail()
    print("\nPrint list:"			)
    linked_list.print_list()
    print("\nReverse linked list"			)
    linked_list.reverse()
    print("\nPrint list:"			)
    linked_list.print_list()
    print("\nString representation of linked list:"			)
    print(SCREAMING_SNAKE_CASE_			)
    print("\nReading/changing Node data using indexing:"			)
    print(f"Element at Position 1: {linked_list[1]}"			)
    UpperCamelCase_			  =						input("Enter New Value: "			).strip()
    print("New list:"			)
    print(SCREAMING_SNAKE_CASE_			)
    print(f"length of linked_list is : {len(SCREAMING_SNAKE_CASE_			)}"			)


if __name__ == "__main__":
 main()
