SEN2212 · 8. hafta · Using heaps as priority queues. Midterm.

Vize tekrarı: sıralama, ağaçlar, BST, AVL, heap

1-8. haftaların tek sayfada özeti: Big-O tablosu, her konunun iz sürme kalıbı ve karışık vize soruları.

lower boundradix sortpreorderinorderpostorderlevel-orderbinary search treeinorder successorAVL treerotationbinary heapbuildHeapheapsortstable sort

Vize haftası. Bu sayfa yeni konu anlatmaz; ilk sekiz haftayı tek yerde toplar. Önce özet tabloya bak, sonra her konunun “sınavda nasıl çözülür” kalıbını oku, en son soruları kâğıt kalemle çöz. Her sorunun cevabını kendi izini çıkarmadan açma.

Vizede karşına çıkacak soru tipleri neredeyse sabittir:

  1. Big-O: bir yapı ya da algoritma için en iyi, ortalama, en kötü süre.
  2. İz sürme: “şu sırayla ekle, ağacı/diziyi çiz”.
  3. Metot yazma: özyinelemeli (recursive) ağaç metotları: yükseklik, yaprak sayısı, toplam, arama.

Büyük tablo

Yapı / algoritmaİşlemEn iyi / ortalamaEn kötüNot
Merge sortsıralamaO(nlog⁡n)O(n \log n)O(nlog⁡n)O(n \log n)kararlı, O(n)O(n) ek bellek
QuicksortsıralamaO(nlog⁡n)O(n \log n)O(n2)O(n^2)yerinde, kararsız
HeapsortsıralamaO(nlog⁡n)O(n \log n)O(nlog⁡n)O(n \log n)yerinde, kararsız
Counting sortsıralamaO(n+k)O(n + k)O(n+k)O(n + k)k = değer aralığı
Radix sortsıralamaO(d(n+k))O(d(n + k))O(d(n+k))O(d(n + k))d basamak, kararlı alt sıralama
Ağaç gezinmepre/in/post/levelO(n)O(n)O(n)O(n)her düğüm bir kez
BSTfind/insert/removeO(log⁡n)O(\log n)O(n)O(n)sıralı eklemede zincir
AVLfind/insert/removeO(log⁡n)O(\log n)O(log⁡n)O(\log n)yükseklik ≤ ~1.44 log n
Binary heapinsertO(1)O(1) ort.O(log⁡n)O(\log n)yukarı süzme
Binary heapdeleteMinO(log⁡n)O(\log n)O(log⁡n)O(\log n)aşağı süzme
Binary heapfindMinO(1)O(1)O(1)O(1)kök
Binary heapbuildHeapO(n)O(n)O(n)O(n)n kez insert O(nlog⁡n)O(n \log n) olurdu

Sıralama: hatırlanacaklar

Alt sınır. Sadece karşılaştırma yapan bir algoritma bir karar ağacıdır. n!n! farklı sıralamanın her biri ayrı bir yaprakta bitmelidir. Yüksekliği h olan ikili ağaçta en fazla 2h2^h yaprak olduğundan:

h≥⌈log⁡2n!⌉=Ω(nlog⁡n)h \ge \lceil \log_2 n! \rceil = \Omega(n \log n)

n   n!      en az karşılaştırma
3   6       3
4   24      5
5   120     7
6   720     10
8   40320   16

Counting ve radix bu sınırı neden geçer? Çünkü karşılaştırma yapmazlar. Değerin kendisini dizi indeksi olarak kullanırlar. Bunun bedeli: değerler küçük tam sayılar (ya da sabit uzunlukta anahtarlar) olmalı.

LSD radix izi. Her geçişte bir basamağa göre kararlı (stable) dağıt, kovaları sırayla topla:

başlangıç  512  34 208  71 645  93 160
birler     160  71 512  93  34 645 208
onlar      208 512  34 645 160  71  93
yüzler      34  71  93 160 208 512 645

TUZAK · radix’te kararlılık. Onlar geçişinde 208 ve 512 farklı kovalara gider, ama aynı kovaya düşen sayılar bir önceki geçişin sırasını korumalı. Kararlılığı bozarsan önceki geçişin işi kaybolur.

Ağaçlar ve gezinme

Şu ağacı ezberden çözebilmelisin:

        A
       / \
      B   C
     / \   \
    D   E   F
       /
      G
preorder   A B D E G C F    (kök, sol, sağ)
inorder    D B G E A C F    (sol, kök, sağ)
postorder  D G E B F C A    (sol, sağ, kök)
level      A B C D E F G    (kuyruk ile)
yükseklik  3, yaprak sayısı 3 (D, G, F)

Preorder + inorder’dan ağaç kurma. Preorder’ın ilk elemanı köktür. Inorder’da kökü bul: solundakiler sol alt ağaç, sağındakiler sağ alt ağaç. Preorder’da sıradaki eleman, sol alt ağacın köküdür. Özyinelemeli devam et.

pre: 5 9 1 3 7 2 8     in: 1 9 7 3 5 2 8

kök 5: in -> [1 9 7 3] 5 [2 8]
sol kök 9: in -> [1] 9 [7 3]
  9'un sağı kök 3: in -> [7] 3
sağ kök 2: in -> 2 [8]

          5
        /   \
       9     2
      / \     \
     1   3     8
        /
       7
post: 1 7 3 9 8 2 5

Sadece preorder + postorder ise ağaç tek değildir (tek çocuklu düğümün çocuğu solda mı sağda mı bilinmez). Inorder şarttır.

BST: ekleme ve silme

45, 20, 60, 10, 30, 50, 70, 25, 35 ekle:

           45
         /    \
       20      60
      /  \    /  \
    10    30 50   70
         /  \
        25   35

Silmenin üç durumu: yaprak ise doğrudan sil. Tek çocuk varsa çocuğu ebeveyne bağla. İki çocuk varsa değerini inorder successor (sağ alt ağacın en solu) ile değiştir, sonra successor’ı sağ alt ağaçtan sil (o en fazla bir çocukludur).

20’yi sil: successor 25.

           45
         /    \
       25      60
      /  \    /  \
    10    30 50   70
            \
             35

Preorder: 45 25 10 30 35 60 50 70. Sonra 45’i silersen successor 50 olur: 50 25 10 30 35 60 70.

AVL: rotasyon seçimi

Ekleme yolunda aşağıdan yukarı çıkarken BF’si +2 ya da -2 olan ilk düğüm rotasyon noktasıdır. Durumu oradan bakarak, eklemenin hangi torunda yapıldığına göre seç:

Ekleme nereyeBFRotasyon
sol çocuğun solu (LL)+2tek sağa
sağ çocuğun sağı (RR)-2tek sola
sol çocuğun sağı (LR)+2önce çocukta sola, sonra sağa
sağ çocuğun solu (RL)-2önce çocukta sağa, sonra sola

40, 20, 60, 10, 30 ekledikten sonra 25 ekle:

önce (25 eklendi)          sonra (LR at 40)
       40                        30
      /  \                     /    \
    20    60                 20      40
   /  \                     /  \       \
  10   30                  10   25      60
      /
    25

40’ın BF’si 2 - 0 = 2, ekleme sol çocuğun (20) sağına gitti: LR. Ortanca değer (30) yukarı çıkar.

Heap: buildHeap ve heapsort

buildHeap dizinin son iç düğümünden (n/2) köke doğru her düğümü aşağı süzer. Çoğu düğüm alt katlarda ve az süzülür; toplam iş O(n)O(n).

[9, 4, 7, 1, 8, 2, 6]   n=7, i=3..1
i=3  7 <-> 2           [9, 4, 2, 1, 8, 7, 6]
i=2  4 <-> 1           [9, 1, 2, 4, 8, 7, 6]
i=1  9 -> 1 -> 4       [1, 4, 2, 9, 8, 7, 6]

Heapsort artan sıra için max-heap kurar (0-indeksli: çocuklar 2i+1, 2i+2). Sonra her adımda kökü (en büyük) dizinin aktif bölümünün sonuna koyar ve heap’i bir küçültür.

[3, 8, 5, 1, 9, 6]
buildHeap   [9, 8, 6, 1, 3, 5]
adım 1      [8, 5, 6, 1, 3 | 9]
adım 2      [6, 5, 3, 1 | 8, 9]
adım 3      [5, 1, 3 | 6, 8, 9]
adım 4      [3, 1 | 5, 6, 8, 9]
adım 5      [1 | 3, 5, 6, 8, 9]

Öncelik kuyruğu ve java.util.PriorityQueue için bu haftanın diğer sayfasına bak.

Sık yapılan hatalar

Yanlış düşünceDoğrusu
Radix’te her geçişte istediğin sıralamayı kullanAlt sıralama kararlı olmalı
Pre + post ile ağaç tek belirlenirInorder gerekir
Silmede successor = sağ çocukSağ alt ağacın en solundaki düğüm
AVL’de BF’si bozuk en üst düğümde döndürYoldaki en alttaki bozuk düğümde
LR’de tek sağa rotasyon yeterÇift rotasyon: önce çocukta sola
buildHeap O(nlog⁡n)O(n \log n)O(n)O(n); n kez insert O(nlog⁡n)O(n \log n)
Artan heapsort için min-heapYerinde artan sıra için max-heap
Tek düğümün yüksekliği 1Bu derste 0; boş ağaç -1

Kendini test et

Sınavdaki gibi İngilizce sorular. Önce kâğıt kalemle çöz, sonra cevabı aç.

Soru 1orta

What is the minimum number of comparisons that any comparison-based algorithm needs, in the worst case, to sort 6 elements?

Cevabı göster
10

Karar ağacının en az 6!=7206! = 720 yaprağı olmalı. Yüksekliği h olan ikili ağacın en fazla 2h2^h yaprağı var: 2h≥7202^h \ge 720. 29=512<720≤1024=2102^9 = 512 < 720 \le 1024 = 2^{10}, yani h=⌈log⁡2720⌉=10h = \lceil \log_2 720 \rceil = 10.

Soru 2orta

Apply LSD radix sort (base 10) to [512, 34, 208, 71, 645, 93, 160]. Give the array after the first pass and after the second pass.

Cevabı göster
[160, 71, 512, 93, 34, 645, 208] then [208, 512, 34, 645, 160, 71, 93]

1. geçiş birler basamağına göre (kararlı): 160(0), 71(1), 512(2), 93(3), 34(4), 645(5), 208(8).
2. geçiş onlar basamağına göre, eşitlerde önceki sıra korunur: 208(0), 512(1), 34(3), 645(4), 160(6), 71(7), 93(9).
3. geçiş yüzler basamağı ile sıralı dizi çıkar: [34, 71, 93, 160, 208, 512, 645].

Soru 3kolay

Which of merge sort, quicksort and heapsort is both stable and O(nlog⁡n)O(n \log n) in the worst case?

  1. merge sort
  2. quicksort
  3. heapsort
  4. none of them
Cevabı göster
merge sort

Merge sort eşitlerde soldakini önce alırsa kararlıdır ve her durumda O(nlog⁡n)O(n \log n). Quicksort'un en kötüsü O(n2)O(n^2) ve kararlı değil. Heapsort O(nlog⁡n)O(n \log n) ama kararlı değil (uzun mesafeli takaslar yapar).

Soru 4kolay

For the tree below, give the postorder and level-order traversals.

        A
       / \
      B   C
     / \   \
    D   E   F
       /
      G
Cevabı göster
post: D G E B F C A; level: A B C D E F G

Postorder = sol, sağ, kök. B'nin altı: D, sonra E'nin altı (G, E), sonra B. Sonra C'nin altı: F, C. En son A.
Level-order: kat kat soldan sağa. A | B C | D E F | G.
(Preorder A B D E G C F, inorder D B G E A C F.)

Soru 5zor

A binary tree has preorder 5 9 1 3 7 2 8 and inorder 1 9 7 3 5 2 8. Give its postorder traversal.

Cevabı göster
1 7 3 9 8 2 5

Preorder'ın ilki kök: 5. Inorder'da 5'in solu {1 9 7 3}, sağı {2 8}.
Sol alt ağaç: preorder'da sıradaki 9 kök. Inorder {1 | 9 | 7 3}: solu 1, sağı {7 3}. Sıradaki 3 kök, inorder {7 3}'te 7 onun solu.
Sağ alt ağaç: kök 2, inorder {2 8} → 8 sağ çocuk.
Postorder: 1, 7, 3, 9, 8, 2, 5.

Soru 6orta

Insert 45, 20, 60, 10, 30, 50, 70, 25, 35 into an empty BST, then delete 20 (use the inorder successor). Give the preorder traversal of the result.

Cevabı göster
45 25 10 30 35 60 50 70

Silmeden önce preorder: 45 20 10 30 25 35 60 50 70.
20'nin iki çocuğu var. Inorder successor = sağ alt ağacın en küçüğü = 25. 20'nin yerine 25 yazılır, sonra sağ alt ağaçtan 25 silinir (yaprak). 30'un solu boşalır.
Sonuç preorder: 45 25 10 30 35 60 50 70.

Soru 7orta

Keys 1, 2, 3, 4, 5, 6, 7 are inserted in this order into (a) a plain BST and (b) an AVL tree. What is the height of each tree? (A single node has height 0.)

Cevabı göster
(a) 6, (b) 2

Düz BST'de sıralı ekleme sağa uzanan bir zincir üretir: 7 düğüm, 6 kenar, yükseklik 6. AVL dört kez RR (tek sola) rotasyonu yapar ve mükemmel ağacı kurar: preorder 4 2 1 3 6 5 7, yükseklik 2.

Soru 8zor

Insert 40, 20, 60, 10, 30, 25 into an empty AVL tree. Which rotation happens, at which node, and what is the preorder traversal afterwards?

Cevabı göster
LR (double) rotation at 40; preorder 30 20 10 25 40 60

25 eklenince yol 40 → 20 → 30 → 25(sol). Yükseklikler: h(20)=2, h(60)=0, 40'ın BF = 2 - 0 = 2.
Ekleme 40'ın SOL çocuğunun SAĞ alt ağacına yapıldı: LR durumu.
Önce 20'de sola rotasyon (30 yukarı), sonra 40'ta sağa rotasyon. Yeni kök 30; solu 20 (çocukları 10 ve 25), sağı 40 (sağ çocuğu 60).

Soru 9orta

Run buildHeap (min-heap, array starting at index 1) on [9, 4, 7, 1, 8, 2, 6]. Give the resulting array.

Cevabı göster
[1, 4, 2, 9, 8, 7, 6]

n = 7, i = n/2 = 3'ten 1'e kadar aşağı süz.
i=3: 7, çocuklar 2 ve 6, küçük 2 → [9, 4, 2, 1, 8, 7, 6]
i=2: 4, çocuklar 1 ve 8 → 1 yukarı → [9, 1, 2, 4, 8, 7, 6]
i=1: 9, çocuklar 1 ve 2 → 1 yukarı; 9 indeks 2'de, çocuklar 4 ve 8 → 4 yukarı → [1, 4, 2, 9, 8, 7, 6]

Soru 10zor

Heapsort (max-heap, 0-indexed) is applied to [3, 8, 5, 1, 9, 6]. Give the array after buildHeap and after the first deleteMax step (swap root with last, percolate down).

Cevabı göster
[9, 8, 6, 1, 3, 5] then [8, 5, 6, 1, 3, 9]

buildHeap: i = 2, 1, 0. i=2: 5 < 6 → [3, 8, 6, 1, 9, 5]. i=1: 8 < 9 → [3, 9, 6, 1, 8, 5]. i=0: 3, büyük çocuk 9 → yukarı; 3 indeks 1'de, büyük çocuk 8 → yukarı → [9, 8, 6, 1, 3, 5].
1. adım: 9 ile son eleman 5 yer değişir → [5, 8, 6, 1, 3 | 9]. 5'i ilk 5 eleman içinde aşağı süz: 8 yukarı, sonra çocuklar 1 ve 3, ikisi de 5'ten küçük → dur: [8, 5, 6, 1, 3, 9].

Soru 11orta

Write a recursive method int height(Node t) for a binary tree, where an empty tree has height -1 and a single node has height 0.

Cevabı göster
null → -1, else 1 + max(height(left), height(right))

Boş ağaç taban durumdur. Diğer her düğüm için iki alt ağacın yüksekliğinin büyüğüne 1 ekle.

static int height(Node t) {
    if (t == null) return -1;
    return 1 + Math.max(height(t.left), height(t.right));
}

Yukarıdaki harfli ağaçta (A...G) sonuç 3 (A → B → E → G). Her düğüm bir kez ziyaret edilir: O(n)O(n).

Soru 12kolay

Give the worst-case time of search in (a) a BST with n nodes, (b) an AVL tree with n nodes, and (c) findMin in a binary min-heap.

Cevabı göster
(a) O(n), (b) O(log n), (c) O(1)

Düz BST sıralı eklemeyle zincire döner, arama O(n)O(n). AVL yüksekliği her zaman O(log⁡n)O(\log n) tuttuğu için arama O(log⁡n)O(\log n). Min-heap'te en küçük her zaman kökte: O(1)O(1). Ama heap'te keyfi bir elemanı aramak O(n)O(n).

Doğrulama: Tüm izler (radix geçişleri, gezinme sıraları, preorder+inorder'dan ağaç kurma, BST silme, AVL rotasyonları, buildHeap, heapsort adımları) Java ile kodlanıp çalıştırıldı (verify/SEN2212/W08R.java, java W08R.java).

Deftere not kartı

Karşılaştırmalı sıralama alt sınırı: ceil(log2 n!) karşılaştırma, Ω(n log n). n=5 → 7, n=6 → 10. Merge O(n log n) her durumda, kararlı, O(n) ek bellek. Quick ortalama n log n, en kötü n^2. Heap n log n, kararlı değil. Counting O(n+k), radix O(d(n+k)); radix her geçişte KARARLI sıralama ister, LSD birlerden başlar. Pre = kök sol sağ, In = sol kök sağ, Post = sol sağ kök, Level = kuyrukla kat kat. Pre + In → ağaç tek: pre'nin ilki kök, in'de böl. BST'de inorder = sıralı. Silme: yaprak sil, tek çocuk bağla, iki çocuk → inorder successor (sağın en solu). BST yükseklik: en iyi log n, sıralı eklemede n-1. AVL: BF = h(sol) - h(sağ) ∈ {-1,0,1}, h(null) = -1. LL → sağa tek, RR → sola tek, LR/RL → çift. Rotasyon yeri: eklenen yoldan yukarı çıkarken BF'si ±2 olan İLK düğüm. Heap: ebeveyn i/2, çocuk 2i, 2i+1 (1-indeksli). insert = yukarı süz, deleteMin = son elemanı köke koy, aşağı süz. buildHeap: n/2'den 1'e aşağı süz, toplam O(n). Heapsort: max-heap, kökü sona at, n log n.