Skip to content
Open
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
62 changes: 62 additions & 0 deletions data_structures/linked_list/doubly_linked_list.py
Original file line number Diff line number Diff line change
@@ -1,3 +1,5 @@
from data_structures.linked_list import singly_linked_list

"""
https://en.wikipedia.org/wiki/Doubly_linked_list
"""
Expand Down Expand Up @@ -187,6 +189,47 @@ def is_empty(self):
"""
return len(self) == 0

def doubly_to_singly(self) -> singly_linked_list.Node | None:
"""
Convert this doubly linked list into a singly linked list.

A new singly linked list is created by copying the data from
each node in the doubly linked list.

Returns
-------
singly_linked_list.Node | None
The head node of the newly created singly linked list.

Example
-------
>>> dll = DoublyLinkedList()
>>> dll.insert_at_tail(1)
>>> dll.insert_at_tail(2)
>>> dll.insert_at_tail(3)
>>> head = dll.doubly_to_singly()
>>> head.data
1
>>> head.next_node.data
2
>>> head.next_node.next_node.data
3
"""

if self.head is None:
return None

doubly_current: Node | None = self.head.next
new_head = singly_linked_list.Node(self.head.data)
singly_current = new_head

while doubly_current:
singly_current.next_node = singly_linked_list.Node(doubly_current.data)
singly_current = singly_current.next_node
doubly_current = doubly_current.next

return new_head


def test_doubly_linked_list() -> None:
"""
Expand Down Expand Up @@ -223,6 +266,25 @@ def test_doubly_linked_list() -> None:
assert len(linked_list) == 9
assert str(linked_list) == "->".join(str(i) for i in range(1, 10))

# Test doubly_to_singly conversion
dll = DoublyLinkedList()
dll.insert_at_tail(1)
dll.insert_at_tail(2)
dll.insert_at_tail(3)

head = dll.doubly_to_singly()

assert head is not None
s_head = head # type: singly_linked_list.Node

assert s_head.data == 1

assert s_head.next_node is not None
assert s_head.next_node.data == 2

assert s_head.next_node.next_node is not None
assert s_head.next_node.next_node.data == 3


if __name__ == "__main__":
from doctest import testmod
Expand Down
Loading