30  Problem Oturumu 9

Pseudopolinom DP oturumu — 0/1 ve sınırsız knapsack, precomputation sinyali ve adversarial minimax

NotOturum bilgisi
  • Solomon’un videosu: YouTube — Problem Session 9 (≈85 dk)
  • OCW sayfası: MIT 6.006 Problem Session 9
  • Seri: MIT 6.006 — Introduction to Algorithms (Spring 2020) — Ders 29 (PS9)
  • Hoca: Justin Solomon
  • Okuma süresi: ≈24 dk
  • DP problem oturumlarının İKİNCİSİ; pseudopolinom dili “liberating” (Solomon 0:26).

30.1 Bu Problem Oturumu Ne Hakkında?

Dokuzuncu problem oturumu (Justin Solomon), dinamik programlama üzerine iki oturumun ikincisi; bu kez pseudopolinom DP odakta dört problemi SRTBOT çerçevesiyle çözer (Şekil 33.1). Solomon “bu set öncekinden kolaydı” der — çünkü pseudopolinom, runtime’da “kullanmaman gereken” sayısal parametreleri (\(k\), \(b\)) kullanmaya izin verir, bu da recurrence kurmayı kolaylaştırır.

“we learned in class about pseudo polynomial time style dynamic programs. Somehow, that language is a little bit liberating.” — Solomon, 0:26

Beş problem planlanmıştı; Solomon dördünü işledi (9-5 “duvar örme” zaman yetmediği için atlandı — bkz. Bölüm 30.7 öncesi son not). Her problem “İfade → Yaklaşım → Çözüm → Karmaşıklık” akışıyla işlenir. Yeni temalar: 0/1 vs sınırsız knapsack, zaman ekseninin topolojik sıra vermesi, toplam-terimli runtime → precomputation sinyali, ve minimax (adversarial) DP.

flowchart TD
    R["Problem Oturumu 9<br/>(DP problem oturumlarının İKİNCİSİ — pseudopolinom)"] --> P1["Problem 1<br/>Coin-Crafting<br/>(0/1 knapsack, O(n²))"]
    R --> P2["Problem 2<br/>Tim kariyer fuarı<br/>(sınırsız + boşaltma, O(nbk))"]
    R --> P3["Problem 3<br/>Protein parsing<br/>(naif → precompute)"]
    R --> P4["Problem 4<br/>Lazy egg drop<br/>(minimax / adversarial)"]
    CORE["Ortak tema:<br/>runtime'ın ŞEKLİ çözümü ele verir<br/>(toplam mı çarpım mı, hangi parametreler)<br/>— pseudopolinom dili 'liberating'"]
    CORE -.-> P1
    CORE -.-> P2
    CORE -.-> P3
    CORE -.-> P4

    classDef root fill:#fef3c7,stroke:#b45309,stroke-width:3px,color:#1f2937
    classDef branch fill:#f3f4f6,stroke:#374151,stroke-width:2px,color:#1f2937
    classDef leaf fill:#fcd34d,stroke:#b45309,stroke-width:2px,color:#1f2937
    class R root
    class P1,P2,P3,P4 branch
    class CORE leaf
Şekil 30.1: Problem Oturumu 9’un kavram haritası: kök (PS9) dört probleme dallanır ve ortadaki ortak tema düğümü dördünü birden yönlendirir. Problem 1 Coin-Crafting’i 0/1 knapsack ile çözer — her nesneden en fazla bir tane, j−1’e geçerek nesneyi tüketir, (n+1)² hücre × O(1) = O(n²) polinom. Problem 2 Tim the Beaver kariyer fuarını SINIRSIZ knapsack + çanta boşaltma ile çözer — aynı stant tekrar tekrar alınır, çanta dolunca eve gidip boşaltılır, zaman hep ileri aktığı için topolojik sırayı zaman verir, kb hücre × O(n) = O(nbk) pseudopolinom. Problem 3 Protein Parsing’i naif v1’den (string-karşılaştırma her adımda, O(|S|·|P|·k) iki dev çarpım) precompute v2’ye (hash + m üyelik tablosu) indirger; runtime’da çarpım değil TOPLAM görmek precomputation sinyalidir, O(k·|P| + k²·|S|). Problem 4 Lazy Egg Drop’u minimax DP ile çözer — yumurta adversarial, min içinde max; topolojik sıra harcanan kaynaktan değil belirsizliğin DARALMASINDAN gelir, O(n³k). Ortak tema — istenen runtime’ın şekli (toplam mı çarpım mı, hangi parametreler) çözümün yapısını ele verir — Solomon’un dört probleme de aynı kapıdan girmesini sağlar.
İpucuYaklaşım — ortak strateji: istenen runtime’ın şeklini hocanın ipucu gibi oku

Dört problemin tamamı aynı refleksle başlar: önce alt problemi (Subproblem) tanımla, sonra “bu alt problemde hangi yerel kararı versem geri kalanı bir küçük alt probleme iner?” diye yerel kaba kuvvet uygula; bu recurrence’ı (Relation) verir. Pseudopolinom dili bu oturumda işi kolaylaştırır: runtime’da \(k\) ve \(b\) gibi sayısal parametreleri kullanmaya izin verince recurrence doğal akar. İncelik istenen runtime’ı bir teşhis aracı gibi okumakta: \(O(nbk)\) gibi bir çarpım doğrudan tablo boyutu × hücre işidir; \(O(k \lvert P \rvert + k^2 \lvert S \rvert)\) gibi bir toplam ise “DP dışında ön-işleme var” der; bir min içinde max ise adversarial bir minimax kurar. Bu oturum, DP kasını bu dört SRTBOT’la pseudopolinom yönünde çalıştırır.

Şekil 30.2 iki knapsack varyantını yan yana motordan gerçek verilerle gösterir: solda Problem 1 (0/1, \(O(n^2)\) polinom), sağda Problem 2 (sınırsız + çanta boşaltma, \(O(nbk)\) pseudopolinom). Tek bir “kapasite içinde max değer” çekirdeği iki farklı kısıtla karşı karşıya gelir; figür her ikisini birden kapsar ve aşağıdaki iki problemin köprüsüdür.

Şekil 30.2: İki knapsack yan yana — Problem 1 ve Problem 2 İMZA. Veri MOTORDAN (P1: P=[8,5,11,6,3] K=[2,1,3,2,1] bütçe 5 → 19 = bitmask; P2: C=[10,4] W=[2,1] t=[1,0] b=2 h=1 k=9 → 24 = eylem-DFS). SOL P1 — 0/1 knapsack (her nesne ≤ 1 kez): 5 nesne kartı (P fiyat üst, K eritme alt), seçilenler (11+5+3) amber yıldızlı; bütçe çubuğu 5 para → 3+1+1 dolu; x(i,j) recurrence kutusu (yap → j−1’e GEÇ / yapma → j−1, her iki dalda nesne tüketilir); sonuç 19 rozeti; ‘(n+1)² × O(1) = O(n²) POLİNOM’. SAĞ P2 — SINIRSIZ + çanta boşaltma: zaman çizgisi 9 dk + motor-optimal eylem dizisi (stant0→eve→stant0→eve→stant1, aynı stant tekrar); çanta doluluk basamak grafiği (b=2’ye dayanınca EVE GİT → b’ye sıfırlanır amber ok); ‘zaman HEP İLERİ → topolojik sıra (Solomon 30:00)’; sonuç 24 rozeti; ‘kb × O(n) = O(nbk) PSEUDOpolinom (k, b runtime’da)’.

30.2 Problem 1: Coin-Crafting — 0/1 Knapsack

İfade. Bir hırsızın \(n\) özdeş altın parası var; bunları eritip \(n\) nesneden bazılarını üretip alıcıya satacak. Nesne \(i\): fiyat \(P_i\), eritme sayısı \(K_i\) (üretmek için gereken para). Her nesneden en fazla bir tane (0/1). Toplam para bütçesiyle geliri maksimize et.

İpucuYaklaşım — iki doğal parametre: hangi nesneyi yaptım + kaç para harcadım

İki doğal parametre var: hangi nesneyi yaptım (nesne indeksi) + kaç para harcadım (kalan bütçe). Bu klasik 0/1 knapsack. Nesne sırası önemsiz olduğu için topolojik sırayı nesne indeksi verir; her nesne için yerel kaba kuvvet ikiye iner — yap ya da yapma. “Her nesneden en fazla bir tane” kısıtı recurrence’ın yapısına gömülür: her iki seçenekte de \(j \to j-1\) ilerler, yani bir kez bakılan nesne tüketilir.

“the two variables here, when I make a new object, is what object did I make? And how many coins did I spend?” — Solomon, 14:30

Şekil 30.2 (sol panel) bu 0/1 knapsack’i motordan gerçek verilerle gösterir: örnek fiyatlar \(P = [8, 5, 11, 6, 3]\) ve eritmeler \(K = [2, 1, 3, 2, 1]\), bütçe \(5\) para için optimal gelir \(19\) — nesneler \(11 + 5 + 3\) seçilir (\(K\) toplamı \(3 + 1 + 1 = 5\), tam bütçe). Bağımsız bitmask tanığı da aynı \(19\)’u verir.

Çözüm. S: \(x(i, j) = i\) para ve ilk \(j\) nesneyle elde edilebilen maksimum gelir. R: iki seçenek — \(j\)’yi yapma \(\to x(i, j-1)\); \(j\)’yi yap (yalnız \(i \ge K_j\) ise) \(\to P_j + x(i - K_j, j-1)\); ikisinin max’ı. T: ikinci indeks (\(j\)) azalır. B: \(x(0, j) = 0\) (para yok), \(x(i, 0) = 0\) (nesne yok). O: \(x(n, n)\).

def coin_craft(P, K, budget=None):               # (n+1)² × O(1) = O(n²)
    n = len(P)
    budget = n if budget is None else budget      # bütçe = n özdeş para
    x = {(i, 0): 0 for i in range(budget + 1)}    # taban: nesne yok → 0
    for j in range(1, n + 1):
        for i in range(budget + 1):
            best = x[(i, j - 1)]                   # j'yi YAPMA → j−1
            if K[j - 1] <= i:                      # j'yi YAP (para yeterli)
                best = max(best, P[j - 1] + x[(i - K[j - 1], j - 1)])
            x[(i, j)] = best                       # her iki dalda da j → j−1
    return x[(budget, n)], x

Karmaşıklık. \((n+1)^2\) alt problem \(\times\ O(1)\) iş = \(O(n^2)\).

NotBonus — SRTBOT’u koda çevirmenin iki yolu

Solomon SRTBOT’u koda çevirmenin iki yolunu gösterdi: memoization (yukarıdan-aşağıya; “zaten hesapladıysam tabloya bak, döndür” — DP’nin sihri tek satırda) ve bottom-up (aşağıdan-yukarıya; \(j\) sütunlarını sırayla doldur, recursion yok). İkisi sabit-çarpan farkıyla eşdeğer; pratikte bottom-up (yığın yükü yok + netlik) tercih edilir. Yukarıdaki kod bottom-up sürümdür.

30.3 Problem 2: Tim the Beaver Kariyer Fuarı — Sınırsız Knapsack + Çanta Boşaltma

İfade. \(n\) stant; nesne \(i\): havalılık \(C_i\), ağırlık \(W_i\), sıra-bekleme \(t_i\); her sıraya girmek \(+1\) dk. Çanta kapasitesi \(b\); eve gidip çanta boşaltma \(h\) dk (sonra \(+1\)). Toplam süre \(k\). Aynı nesneden birden çok alınabilir (sınırsız). \(k\) dakikada maksimum toplam havalılığı bul; hedef \(O(nbk)\).

İpucuYaklaşım — iki kısıt: süre ve ağırlık; topolojik sırayı zaman verir

İki kısıt var: süre ve çanta ağırlığı. Kilit: çanta boşaltılabildiği için ağırlık monotonik azalmaz — ama boşaltmak da süre harcar. Yine de zaman hep ileri akar → bir adım atan her seçenek ya işi bitirir ya kalan süreyi kesin azaltır; bu da topolojik sırayı zamandan doğurur (boşaltmak ağırlığı geri yükselttiğinde bile). Aynı stant tekrar tekrar alınabildiği için bu sınırsız knapsack’tir: nesne indeksinde ileri geçmek yerine her seçenekte tüm stantlar yeniden taranır.

“time always moves forward for Tim the Beaver… that’s what’s going to give us our topological order.” — Solomon, 30:00

Şekil 30.2 (sağ panel) bu sınırsız knapsack’i motordan gerçek verilerle gösterir: iki stant \((C, W, t) = (10, 2, 1)\) ve \((4, 1, 0)\), çanta \(b = 2\), ev \(h = 1\), süre \(k = 9\) için optimal havalılık \(24\) — motor-optimal senaryo stant 0 → eve → stant 0 → eve → stant 1 (\(10 + 10 + 4\), aynı stant tekrar), tam \(9\) dakikayı kullanır. Bağımsız eylem-dizisi DFS tanığı da \(24\) verir.

Çözüm. S: \(x(i, j) = i\) dakika ve çantada \(j\) ağırlık-yeri kalmışken maksimum havalılık. R: üç tip seçeneğin max’ı — (1) pes et \(\to 0\); (2) her stant \(\bar{m}\) için: \(C_{\bar{m}} + x(i - t_{\bar{m}} - 1,\ j - W_{\bar{m}})\) (uygunsa: \(i - t_{\bar{m}} - 1 \ge 0 \wedge j - W_{\bar{m}} \ge 0\)); (3) eve git: \(x(i - h - 1,\ b)\) (havalılık yok, ağırlık-yeri \(b\)’ye sıfırlanır; \(i - h - 1 \ge 0\) ise). T: her seçenek ya biter ya süreyi azaltır. B: \(x(0, j) = 0\). O: \(x(k, b)\).

def career_fair(C, W, t, b, h, k):               # kb × O(n) = O(nbk)
    n = len(C)
    x = {(0, j): 0 for j in range(b + 1)}         # taban: süre yok → 0
    for i in range(1, k + 1):                     # zaman artan (topolojik)
        for j in range(b + 1):
            best = 0                              # (1) pes et
            for m in range(n):                    # (2) stant m (SINIRSIZ tekrar)
                ii, jj = i - t[m] - 1, j - W[m]
                if ii >= 0 and jj >= 0:
                    best = max(best, C[m] + x[(ii, jj)])
            if i - h - 1 >= 0:                     # (3) eve git → yer b'ye SIFIRLANIR
                best = max(best, x[(i - h - 1, b)])
            x[(i, j)] = best
    return x[(k, b)], x

Karmaşıklık. \(kb\) alt problem \(\times\ O(n)\) iş (stantlar üzerinde döngü) = \(O(nbk)\). Pseudopolinom: \(k\) ve \(b\) runtime’da görünür — girdi boyutunda değil, sayısal değerlerinde.

30.4 Problem 3: Protein Parsing — Precomputation ile Hızlandırma

İfade. ACTG’den oluşan DNA dizisi \(S\); uzunluğu \(\le k\) olan marker listesi \(P\). \(S\)’yi alt-dizilere böl (division); değer = \(P\)’de olan parça sayısı. Maksimum değeri bul; hedef \(O(k \lvert P \rvert + k^2 \lvert S \rvert)\).

İpucuYaklaşım — toplam-terimli runtime precomputation sinyalidir

Önce naif DP kurulur, sonra runtime düzeltilir. Asıl ipucu istenen runtime’ın şeklinde: \(O(k \lvert P \rvert + k^2 \lvert S \rvert)\) bir toplam, klasik “alt problem × iş” formülünün verdiği çarpım değil. Çoğu DP bir tablo doldurur ve runtime bir çarpımdır; bir toplam görünce “DP dışında ön-işleme (precomputation) var” diye okumak gerekir. Burada ön-işleme, \(P\) marker’larını hash’lemek ve \(S\)’nin her aralığının markerlığını bir \(m\) tablosuna doldurmaktır; DP kısmı ondan sonra tabloyu \(O(1)\) okur.

“I see two terms. Most of our dynamic programming things involve filling in a table, where you would expect there to be a product. So… maybe I have to do some pre-computation.” — Solomon, 56:30

Şekil 30.3 bu iki aşamayı motordan gerçek verilerle gösterir: $S = $ ACTGACTGA ve \(P = \{\)ACT, GA, TGA, CT\(\}\) için maksimum değer \(4\) — optimal bölünme ACT \(\mid\) GA \(\mid\) CT \(\mid\) GA, dört markerla dokuz harfi tam döşer. Üç bağımsız tanık (naif v1, precompute v2, tüm-bölünmeler brute) birebir \(4\) verir.

Çözüm — v1 (naif, yavaş). S: \(x(i) = S[i{:}]\) sonekinin maksimum değeri. R: \(x(i) = \max(\) \(x(i+1)\) [karakteri atla, değer yok], her marker için: marker \(S\)’ye \(i\)’de uyuyorsa \(1 + x(i + \lvert \text{marker} \rvert)\) \()\). T: \(i\) artar. B: \(x(\lvert S \rvert) = 0\). O: \(x(0)\). Süre: \(\lvert S \rvert\) alt problem \(\times \lvert P \rvert\) marker \(\times\ O(k)\) string-karşılaştırma = \(O(\lvert S \rvert \cdot \lvert P \rvert \cdot k)\) — iki büyük sayının çarpımı, çok yavaş.

Çözüm — v2 (precomputation). \(m[i, j] = 1\) eğer \(S[i{:}j] \in P\), yoksa \(0\). (1) \(P\)’deki tüm string’leri hash’le \(\to O(k \lvert P \rvert)\) (birinci terim). (2) \(m\)’i doldur: her \(i\) için \(j = i+1 \dots i+k\) (uzunluk \(\le k\)), \(S[i{:}j]\)’yi hash’le \(O(k)\) + \(P\)-hash’te ara \(\to O(k^2 \lvert S \rvert)\) (ikinci terim). Revize R′: \(x(i) = \max_{j \in 1 \dots k} (\) \(m[i, i+j] + x(i+j)\) \()\). DP kısmı \(O(\lvert S \rvert \cdot k)\) — diğer terimlerden küçük.

(İndeks köprüsü: prose, kaynaktaki gibi \(m\)’in ikinci indeksini bitiş konumu olarak kullanır — \(m[i, j]\), parça \(S[i{:}j]\). Aşağıdaki kod ve figür ise ikinci indeksi parça uzunluğu alır: kodun \(m[i][j]\)’si, prose’un \(m[i, i+j]\)’sine denktir.)

def protein_v2(S, P, kmax):                      # O(k·|P| + k²·|S|)
    n = len(S)
    pset = set(P)                                # (1) P'yi hash'le — O(k·|P|)
    m = [[0] * (kmax + 1) for _ in range(n + 1)] # (2) m[i][j] üyelik tablosu
    for i in range(n):                           #     — O(k²·|S|)
        for j in range(1, min(kmax, n - i) + 1):
            if S[i:i + j] in pset:
                m[i][j] = 1
    x = [0] * (n + 1)                            # (3) küçük DP — O(|S|·k)
    for i in range(n - 1, -1, -1):
        best = 0
        for j in range(1, min(kmax, n - i) + 1):
            best = max(best, m[i][j] + x[i + j])  # yalnız TABLOYU okur
        x[i] = best
    return x[0], m

Karmaşıklık. \(O(k \lvert P \rvert + k^2 \lvert S \rvert)\). İlginç: tüm precomputation’dan sonra DP kısmı runtime’da önemsiz kalır.

Şekil 30.3: Protein parsing: naif tekrar-hesap vs PRECOMPUTE — Problem 3. Veri MOTORDAN (S=ACTGACTGA, P={ACT,GA,TGA,CT}, k=3, üç tanık v1==v2==brute==4, m tablosunda 8 adet 1). ÜST: DNA şeridi 9 harf kutu + optimal bölünme ACT|GA|CT|GA (4 amber marker bloğu) + sağda P marker listesi (kullanılanlar ✓). ALT: iki-aşamalı boru hattı — v1 naif (soluk kırmızı, O(|S|·|P|·k) iki dev çarpım YAVAŞ) → ‘önce HESAPLA’ oku → v2 üç precompute kutusu: (1) P → hash O(k·|P|), (2) m[i][j] üyelik tablosu mini görsel (1’ler amber) O(k²·|S|), (3) küçük DP O(|S|·k); toplam runtime O(k·|P| + k²·|S|) rozeti; ‘runtime’da TOPLAM görüyorsan precompute sinyali (Solomon 56:30)’.

30.5 Problem 4: Lazy Egg Drop — Minimax DP

İfade. \(n\) katlı bina (kat yükseklikleri \(h(i)\), sıralı), \(k\) yumurta. Yumurtanın kırılmadan atılabildiği en yüksek katı bul. Her atış maliyeti = inilen kat yüksekliği (merdiven inip kontrol). Yumurta kırılırsa üst sınır \(+\) bir yumurta gider; kırılmazsa geri alınır (yeniden kullanılır), alt sınır. Toplam yüksekliği (en kötü durumda) minimize et; hedef \(O(n^3 k)\).

İpucuYaklaşım — adversarial yumurta: belirsizlik aralığını izle, min içinde max kur

Bu bir deney tasarımı problemi. Belirsiz kat aralığı hep bağlantılıdır (bir kat kırılırsa üstündeki tüm katlar da kırılır), bu yüzden durumu bir aralık \([i, j]\) olarak izlemek yeterli. Yumurta adversarial kabul edilir: kırılır/kırılmaz seçimini en çok işi yaptıracak şekilde yapar, çünkü en kötü durumu sınırlamaya çalışıyoruz. Bu da recurrence’ı bir minimax yapar — biz hangi kattan atacağımızı seçerek maliyeti minimize ederiz, yumurta sonucu seçerek maliyeti maksimize eder (min içinde max).

“the egg might be an adversarial egg… we’re trying to upper bound the amount of work… and I’m trying to design a procedure that minimizes my work.” — Solomon, 1:15:15

Şekil 30.4 bu minimax’ı motordan gerçek verilerle gösterir: \(n = 6\) kat, \(h[f] = f\), \(k = 2\) yumurta için minimum en-kötü maliyet \(14\) — DP’nin ilk atışı kat \(f = 2\), kırılırsa \([1, 1]\)’e \(1\) yumurta, kırılmazsa \([3, 6]\)’ya \(2\) yumurta düşer. Bağımsız politika-simülasyonu tanığı yedi gerçek eşiğin hepsinde doğru eşiği bulur ve en kötü maliyetini tam \(14\) (adversarial = en kötü gerçek eşik) verir. \(k = 1\) tek-yumurta hâli zorunlu aşağıdan-yukarı tarama yapar (\(\Sigma h = 21\)); yumurta arttıkça maliyet \([21, 14, 12, 12]\) doymaya gider.

Çözüm. S: $x(i, j, e) = $ belirsiz katlar \([i, j]\) ve \(e\) yumurta kalmışken minimum toplam yükseklik. R (minimax): \(x(i, j, e) = \min_{f \in [i, j]} [\ h(f) + \max(\ x(i, f-1, e-1)\) [kırıldı], \(x(f+1, j, e)\) [kırılmadı] ) ]$. T: belirsizlik genişliği \(j - i\) kesin azalır (yumurta harcaması değil!) → topolojik. B: \(x(i, j, 0) = \infty\) (yumurta bitti ama kat belirsiz — min’de asla seçilmez); \(x(i, i-1, e) = 0\) (aralık tek kata indi). O: \(x(1, n, k)\).

def egg_drop(h, k):                              # n²k × O(n) = O(n³k)
    n = len(h) - 1
    memo, choice = {}, {}

    def x(i, j, e):
        if j < i:    return 0                     # aralık çözüldü
        if e == 0:   return INF                   # yumurtasız belirsizlik
        if (i, j, e) in memo: return memo[(i, j, e)]
        best, bf = INF, None
        for f in range(i, j + 1):                 # hangi kattan atayım? (MIN)
            cand = h[f] + max(x(i, f - 1, e - 1),  # kırıldı  (yumurta -1)  ┐ adversarial
                              x(f + 1, j, e))      # kırılmadı (aralık üstü) ┘ (MAX)
            if cand < best:
                best, bf = cand, f
        memo[(i, j, e)] = best; choice[(i, j, e)] = bf
        return best

    return x(1, n, k), memo, choice

Karmaşıklık. \(n^2\) (iki kat indeksi) \(\times\ k\) (yumurta) alt problem \(\times\ O(n)\) (\(f\) döngüsü) = \(O(n^3 k)\).

Şekil 30.4: Lazy egg drop: minimax DP + politika simülasyonu — Problem 4 İMZA. Veri MOTORDAN (h=[0,1,2,3,4,5,6], k=2 → x(1,6,2)=14; politika-sim 7 eşik HEPSİ doğru + max maliyet 14; ilk atış f=choice[(1,6,2)]=2; k=1 → Σh=21; doyma [21,14,12,12]). SOL: 6 katlı bina, DP’nin ilk atışı f=2 amber vurgu; kırıldı dalı (amber, [1,1] e=1) ve kırılmadı dalı (slate, [3,6] e=2); minimax kutusu x(i,j,e)=min_f[h(f)+max(kırıldı,kırılmadı)] + ‘yumurta ADVERSARIAL (Solomon 1:15:15)’; topolojik-sıra rozeti ‘belirsizlik j−i DARALIR (yumurtadan değil)’. SAĞ ÜST: politika-simülasyon tablosu — 7 gerçek eşik t=0..6 için DP maliyeti [3,3,10,14,14,13,13], max=14 amber; ‘DP politikası HER eşikte doğru eşiği bulur, en kötü == x(1,n,k)=14 adversarial tanık’. SAĞ ALT: doyma eğrisi k=1..4 → [21,14,12,12], 4. yumurta işe yaramaz (belirsizlik-daralması baskın).

Atlanan 5. problem (duvar örme): Karo dizerek duvar örme; runtime üstel ama problem buna izin verir — “küçük parametrelerde üstel” kabul, yasak olan iki dev üstelin çarpımı. Solomon zaman yetmediği için işlemedi (transkript 1:24:34).

30.6 Ne Öğrendik?

ÖnemliAltı Taşınabilir Araç

Bu oturum, DP problem oturumlarının ikincisiydi ve SRTBOT çerçevesini dört pseudopolinom problemde uyguladı:

  1. 0/1 vs sınırsız knapsack (P1 vs P2): “her nesneden bir tane” (\(j-1\)’e geç) \(\leftrightarrow\) “sınırsız” (aynı indekste kal / her seçeneği tara). İkisi de iki-parametreli (bütçe + nesne/zaman).
  2. Zaman = topolojik sıra (P2): ağırlık geri artsa bile (çanta boşaltma), zaman hep ilerlediği için sıra garanti. “\(t\) hem zaman hem topological order”.
  3. SRTBOT → kod (P1): memoization (top-down, “zaten hesapladıysam döndür”) vs bottom-up (tabloyu sırayla doldur); sabit-çarpan eşdeğer, genelde bottom-up tercih.
  4. Toplam-terimli runtime → precomputation (P3): runtime’da çarpım değil toplam görürsen, DP dışında ön-işleme (hash + tablo) yap; DP kısmı küçülür.
  5. Minimax DP (P4): adversarial sonuç (yumurta kırılır/kırılmaz) → min içinde max; topolojik sıra “harcanan kaynak”tan değil belirsizlik daralmasından gelebilir.
  6. “Hocayı teşhis et”: istenen runtime’ın şekli (toplam mı çarpım mı, hangi parametreler) çözümün yapısını ele verir.

30.7 Sonraki

UyarıDers 30 (PS10): Problem Oturumu 10 (Quiz 3 Tekrarı) — Jason Ku

Sırada Ders 30 (PS10): Problem Oturumu 10 (Quiz 3 Tekrarı) var — bu kez hoca değişir, Jason Ku ile DP ve karmaşıklık bloğunun kapanış tekrarını yaparız. Bu oturumdaki pseudopolinom + minimax sezgileri ve “runtime’ı teşhis et” refleksi, Quiz 3 hazırlığının çekirdeğidir.