Skip to content

Commit 57041bb

Browse files
author
Aman Kumar
committed
add linked list
1 parent 8434192 commit 57041bb

18 files changed

+653
-12
lines changed

bst/bst.rb

+69-9
Original file line numberDiff line numberDiff line change
@@ -7,24 +7,31 @@ def initialize(values = [])
77
values.each { |value| insert(value) } if values.any?
88
end
99

10-
def insert(value)
11-
insert_helper(value)
12-
end
13-
1410
def print
1511
puts inorder(@root).to_s
1612
end
1713

18-
def insert_helper(value, node = @root)
14+
def insert(value, node = @root)
1915
if node.nil?
2016
node = TreeNode.new(value)
2117
@root = node if @root.nil?
2218
return node
2319
end
2420
if value < node.val
25-
node.left.nil? ? node.left = TreeNode.new(value) : insert_helper(value, node.left)
21+
node.left = insert(value, node.left)
2622
elsif value > node.val
27-
node.right.nil? ? node.right = TreeNode.new(value) : insert_helper(value, node.right)
23+
node.right = insert(value, node.right)
24+
end
25+
node
26+
end
27+
28+
def search(val, node = @root)
29+
return false if node.nil?
30+
31+
case val <=> node.val
32+
when 1 then search(val, node.right)
33+
when -1 then search(val, node.left)
34+
when 0 then true
2835
end
2936
end
3037

@@ -36,9 +43,62 @@ def inorder(node, output = [])
3643
inorder(node.right, output)
3744
output
3845
end
46+
47+
def min(node = @root)
48+
return nil if node.nil?
49+
50+
current = node
51+
while current
52+
min = current.val
53+
current = current.left
54+
end
55+
min
56+
end
57+
58+
def max(node = @root)
59+
return nil if node.nil?
60+
61+
current = node
62+
while current
63+
max = current.val
64+
current = current.right
65+
end
66+
max
67+
end
68+
69+
def delete(val, node = @root)
70+
return if node.nil?
71+
72+
if val < node.val
73+
node.left = delete(val, node.left)
74+
elsif val > node.val
75+
node.right = delete(val, node.right)
76+
elsif node.left.nil? && node.right.nil?
77+
# leaf node
78+
return nil
79+
elsif node.left.nil? # only left child
80+
return node.right
81+
elsif node.right.nil? # only right child
82+
return node.left
83+
else
84+
# both left and right subtree
85+
replacement = min(node.right)
86+
node.val = replacement
87+
node.right = delete(replacement, node.right)
88+
return node
89+
90+
end
91+
node
92+
end
3993
end
4094

41-
bst = BST.new([4, 33, 4, 5, 6, 42, 7])
95+
bst = BST.new([10, 2, 33, 4, 5, 3, 42])
4296
bst.print
4397

44-
puts bst.root.to_s
98+
# puts bst.search(4)
99+
# puts bst.min
100+
101+
# puts bst.max
102+
103+
puts bst.delete(4)
104+
puts bst.print

linklist/delete

Whitespace-only changes.
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,32 @@
1+
# Given a linked list, return the node where the cycle begins. If there is no cycle, return null.
2+
3+
require_relative './linklist'
4+
5+
def detectCycle(head)
6+
slow = head
7+
fast = head
8+
while slow && fast && fast.next
9+
10+
slow = slow.next
11+
fast = fast.next.next
12+
13+
next unless slow == fast
14+
15+
slow = head
16+
17+
while slow != fast
18+
slow = slow.next
19+
fast = fast.next
20+
end
21+
22+
return fast
23+
end
24+
nil
25+
end
26+
27+
# ll = LinkList.new([1, 2, 3, 4, 5, 6], 2)
28+
# puts detect_cycle(ll.head)
29+
#
30+
#
31+
ll = LinkList.new([1, 2], 0)
32+
puts detectCycle(ll.head)

linklist/detect_cycle_hashing.rb

+47
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,47 @@
1+
# Given a linked list, return the node where the cycle begins. If there is no cycle, return null.
2+
# Input: head = [3,2,0,-4], pos = 1
3+
# Output: tail connects to node index 1
4+
# Explanation: There is a cycle in the linked list, where tail connects to the second node.
5+
6+
require_relative './linklist'
7+
8+
# using hashing
9+
def detect_cycle_hasing(head)
10+
return false if head.nil?
11+
12+
current = head
13+
visited = { current.object_id => 0 }
14+
index = 1
15+
while current.next
16+
puts visited
17+
return "tail connects to node index #{visited[current.next.object_id]}" if visited[current.next.object_id]
18+
19+
visited[current.next.object_id] = index
20+
current = current.next
21+
index += 1
22+
end
23+
24+
'no cycle'
25+
end
26+
27+
# LeetCode submission
28+
def detectCycle(head)
29+
return nil if head.nil?
30+
31+
current = head
32+
visited = { current.object_id => 0 }
33+
index = 1
34+
while current.next
35+
return current.next if visited[current.next.object_id]
36+
37+
visited[current.next.object_id] = index
38+
current = current.next
39+
index += 1
40+
end
41+
42+
nil
43+
end
44+
45+
ll = LinkList.new([1, 2, 3, 4, 5, 6], 5)
46+
# ll.print
47+
puts detect_cycle_hasing(ll.head)

linklist/detect_cycle_one_by_one.rb

+39
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,39 @@
1+
# Given a linked list, return the node where the cycle begins. If there is no cycle, return null.
2+
3+
require_relative './linklist'
4+
5+
def detect_cycle(head)
6+
return nil if head.nil?
7+
8+
slow = head
9+
fast = head.next
10+
while slow && fast && fast.next
11+
slow = slow.next
12+
fast = fast.next.next
13+
if slow == fast
14+
find_node(head, slow)
15+
break
16+
end
17+
end
18+
end
19+
20+
def find_node(head, loop_node)
21+
ptr1 = head
22+
while true
23+
ptr2 = loop_node
24+
25+
ptr2 = ptr2.next while ptr2.next != loop_node && ptr2.next != ptr1
26+
if ptr2.next == ptr1
27+
# ptr2 is last node of loop
28+
# TO remove loop, we can just make ptr2.next = None
29+
puts ptr2.val
30+
return ptr2
31+
else
32+
ptr1 = ptr1.next
33+
end
34+
end
35+
end
36+
37+
ll = LinkList.new([1, 2, 3, 4, 5, 6], 0)
38+
# ll.print
39+
puts detect_cycle(ll.head)

linklist/has_cycle.rb

+34
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,34 @@
1+
require_relative './linklist'
2+
3+
# Floyd's Tortoise and Hare Algorithm
4+
def has_cycle?(head)
5+
return false if head.nil?
6+
7+
slow = head
8+
fast = head
9+
while !slow.nil? && !fast.nil? && !fast.next.nil?
10+
slow = slow.next
11+
fast = fast.next.next
12+
return true if slow == fast
13+
end
14+
false
15+
end
16+
17+
# using hashing
18+
def has_cycle1?(head)
19+
return false if head.nil?
20+
21+
visited = {}
22+
23+
while head
24+
return true if visited[head.object_id]
25+
26+
visited[head.object_id] = true
27+
head = head.next
28+
end
29+
30+
false
31+
end
32+
33+
ll = LinkList.new([1, 2, 3, 4, 5, 6], 3)
34+
puts has_cycle1?(ll.head)
+28
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,28 @@
1+
def getIntersectionNode(headA, headB)
2+
return nil if headA.nil? || headB.nil?
3+
4+
a_pointer = headA
5+
b_pointer = headB
6+
7+
# iterate till both pointers point to the same node
8+
while a_pointer != b_pointer
9+
10+
# once a_pointer reaches end of the headA, point it to start of head B
11+
# for A = totally 5 nodes + 2 nodes to reach intersection point.
12+
a_pointer = if a_pointer.nil?
13+
headB
14+
else
15+
a_pointer.next
16+
end
17+
18+
# once b_pointer reaches end of the headB, point it to start of head A
19+
# for B = totally 3 nodes + 4 nodes to reach intersection point.
20+
b_pointer = if b_pointer.nil?
21+
headA
22+
else
23+
b_pointer.next
24+
end
25+
end
26+
# at this point both of the pointers will be pointing to the same node.
27+
a_pointer
28+
end
+16
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,16 @@
1+
def getIntersectionNode(headA, headB)
2+
return nil if headA.nil? || headB.nil?
3+
4+
visited = {}
5+
while headA
6+
visited[headA.object_id] = true
7+
headA = headA.next
8+
end
9+
10+
while headB
11+
return headB if visited.has_key? headB.object_id
12+
13+
headB = headB.next
14+
end
15+
nil
16+
end
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,37 @@
1+
def getIntersectionNode(headA, headB)
2+
return nil if headA.nil? || headB.nil?
3+
4+
l1 = length(headA)
5+
l2 = length(headB)
6+
diff = (l1 - l2).abs
7+
8+
if l1 > l2
9+
largerH = headA
10+
smallerH = headB
11+
else
12+
largerH = headB
13+
smallerH = headA
14+
end
15+
16+
while largerH.next && diff > 0
17+
largerH = largerH.next
18+
diff -= 1
19+
end
20+
21+
while largerH != smallerH
22+
largerH = largerH.next
23+
smallerH = smallerH.next
24+
end
25+
largerH
26+
end
27+
28+
def length(node)
29+
return 0 if node.nil?
30+
31+
count = 0
32+
while node
33+
count += 1
34+
node = node.next
35+
end
36+
count
37+
end

0 commit comments

Comments
 (0)