Linked List
Kompleksitas Operasi
Contoh Implementasi
package main
import "fmt"
// Node merepresentasikan satu elemen dalam linked list
type Node struct {
Value int
Next *Node
}
// LinkedList adalah struktur yang memegang head dari list
type LinkedList struct {
Head *Node
}
// Insert menambahkan node baru di awal list
// Kompleksitas Waktu: O(1) - hanya operasi pointer
// Kompleksitas Ruang: O(1) - satu node baru
func (ll *LinkedList) Insert(value int) {
newNode := &Node{Value: value}
// Node baru menunjuk ke head yang lama
newNode.Next = ll.Head
// Head sekarang menunjuk ke node baru
ll.Head = newNode
}
// Delete menghapus node pertama dengan value tertentu
// Kompleksitas Waktu: O(n) - mungkin perlu traverse seluruh list
// Kompleksitas Ruang: O(1) - tidak ada alokasi memori tambahan
func (ll *LinkedList) Delete(value int) bool {
// Kasus khusus: list kosong
if ll.Head == nil {
return false
}
// Kasus khusus: node yang akan dihapus adalah head
if ll.Head.Value == value {
ll.Head = ll.Head.Next
return true
}
// Traverse untuk mencari node sebelum node yang akan dihapus
current := ll.Head
for current.Next != nil {
if current.Next.Value == value {
// Skip node yang akan dihapus dengan menghubungkan
// node sebelumnya langsung ke node setelahnya
current.Next = current.Next.Next
return true
}
current = current.Next
}
return false
}
// Reverse membalik urutan linked list
// Kompleksitas Waktu: O(n) - satu pass melalui list
// Kompleksitas Ruang: O(1) - hanya menggunakan tiga pointer
func (ll *LinkedList) Reverse() {
var prev *Node = nil
current := ll.Head
// Ide: untuk setiap node, ubah arah pointer Next-nya
// untuk menunjuk ke node sebelumnya
for current != nil {
// Simpan node berikutnya sebelum kita mengubah pointer
nextTemp := current.Next
// Balik pointer current untuk menunjuk ke prev
current.Next = prev
// Gerakkan prev dan current satu langkah ke depan
prev = current
current = nextTemp
}
// Setelah loop, prev adalah node terakhir (head baru)
ll.Head = prev
}
// HasCycle mendeteksi apakah linked list memiliki cycle
// Kompleksitas Waktu: O(n) - dalam kasus terburuk traverse seluruh list
// Kompleksitas Ruang: O(1) - hanya dua pointer
func (ll *LinkedList) HasCycle() bool {
if ll.Head == nil {
return false
}
// Floyd's Cycle Detection Algorithm (Tortoise and Hare)
// Slow bergerak 1 step, fast bergerak 2 steps
// Jika ada cycle, mereka pasti akan bertemu
slow := ll.Head
fast := ll.Head
for fast != nil && fast.Next != nil {
slow = slow.Next // Bergerak 1 step
fast = fast.Next.Next // Bergerak 2 steps
// Jika slow dan fast bertemu, ada cycle
if slow == fast {
return true
}
}
// Fast mencapai akhir, tidak ada cycle
return false
}
// Print menampilkan semua elemen dalam list
func (ll *LinkedList) Print() {
current := ll.Head
for current != nil {
fmt.Printf("%d -> ", current.Value)
current = current.Next
}
fmt.Println("nil")
}Studi Kasus: Merge Two Sorted Lists
Penjelasan Kompleksitas untuk Cycle Detection
Last updated