Bottom View of Binary Tree
root dizisi bir ikili ağaç tutar: kök 0 indeksinde, i indeksinin çocukları 2i+1 (sol) ve 2i+2 (sağ) indekslerinde, boş bir yer için -1 kullanılır ve sonda fazladan -1 değerleri bulunabilir.
Kök 0 sütunundadır; sola doğru bir adım bir sütun sola, sağa doğru bir adım bir sütun sağa ilerletir. Aşağıdan bakıldığında her sütun en derindeki düğümü gösterir; aynı derinlikte birden fazla düğüm varsa, soldan sağa okunduğunda o seviyedeki son düğüm (daha büyük indeksli olan) seçilir. Gördüğünüz değerleri, en soldaki sütundan başlayarak döndürün.
Fonksiyon
- rootinteger-array
- yığın sırasındaki ağaç, boş bir konum için -1
- Döndürürinteger-array
- her sütunda aşağıdan görülen değer, en soldaki sütundan başlayarak
Kısıtlar
1 ≤ root.length ≤ 32767- Her
root[i],-1ya da0 ≤ root[i] ≤ 104koşulunu sağlayan bir değerdir ve hiçbir değer iki kez görünmez. root[0]hiçbir zaman-1değildir, dolayısıyla ağaçta en az bir düğüm vardır.- Dizi, son düğümden sonra fazladan
-1girdileriyle bitebilir. - Boş bir noktanın her iki çocuğu da boştur ve ağacın en fazla
14seviyesi vardır.
Örnekler
- Girdi
- root = [5, 2, 9, 4, 7, 1, 6]
- Çıktı
- [4, 2, 1, 9, 6]
- Açıklama
- 0. sütunda
5bulunur ve iki seviye aşağıda7(indeks 4) ile1(indeks 5) bulunur.1aynı seviyede daha sonra geldiği için görünür. -2, -1, 1 ve 2. sütunlarda4,2,9ve6bulunur.
- Girdi
- root = [1, 2, 3, -1, 4, -1, -1, -1, -1, 5]
- Çıktı
- [5, 4, 3]
- Açıklama
- -1. sütun
2değerini ve iki seviye aşağıda5değerini (indeks 9) içerir, bu yüzden5görürsün. 0. sütunda, kökün altında4bulunur. 1. sütunda yalnızca3bulunur.
- Girdi
- root = [8, -1, -1, -1]
- Çıktı
- [8]
- Açıklama
- Kökten sonraki her konum
-1olur; bu nedenle8tek düğümdür ve 0 numaralı sütun tek sütundur.
Ek soru
Bir sütunun en derin düzeyinde eşitlik varsa soldan sağa tüm eşit düğümler döndürülmeli. Genişlik öncelikli sürüm nasıl değişirdi? 1. örnekte 0. sütun ne verirdi?
İpuçları
Tek tek açın. Her biri biraz daha fazlasını gösterir.
Sütunları numaralandırın: kök 0'dır, sola doğru bir adım 1 çıkarır ve sağa doğru bir adım 1 ekler. Aşağıdan bakıldığında bir sütundaki hangi düğümü görürsünüz ve o sütunun iki düğümü aynı seviyede bulunursa ne olur?
Düğümleri seviye seviye, her seviyede soldan sağa ziyaret edin ve her düğümün değerini bulunduğu sütuna yazarak önceki değerin üzerine yazın. Sonunda her sütunda ne kalır?
(indeks, sütun) çiftlerinden oluşan bir kuyruk kullanın ve sol çocuğu sağ çocuktan önce kuyruğa ekleyin. Her düğüm için sütunun değerini üzerine yazın, en küçük ve en büyük sütunu takip edin ve sonunda sütunları sırayla okuyun.
Çözüm
Her sütun en derin düğümünü gösterir ve eşitlik durumunda seviye sıralamasında daha sonra gelen düğüm seçilir. Genişlik öncelikli arama düğümleri seviye sırasıyla ziyaret eder; bu nedenle bir sütunda ziyaret ettiği son düğüm yanıttır: her düğümün kendi sütunundaki yuvanın üzerine yazmasına izin verin.
Sütun başına derinlik öncelikli aramadaki en derin düğüm
Sezgi
Ağacı derinlik öncelikli dolaşarak her düğüme sütununu ve derinliğini verin; her sütun için şimdiye kadarki en derin düğümün derinliğini ve değerini tutun.
Sol alt ağacı sağ alt ağaçtan önce ziyaret etmek, bir seviyedeki düğümlerle soldan sağa karşılaşılmasını sağlar; bu nedenle istediğiniz düğüm, karşılaşılan son düğümdür: derinlik büyük veya eşit olduğunda değeri değiştirin. Örnek 1'de dolaşma, sütun 0'da derinlik 2'de hem 7 hem de 1 ile karşılaşır ve sütunu 1 alır.
Sütunlar kesintisiz bir aralık oluşturur; bu yüzden en küçüğünü ve en büyüğünü takip edin, ardından aradaki tüm sütunları okuyun. Düğüm başına bir ziyaret, O(n) zaman alır; h seviyeli bir ağaçta özyineleme h çağrı derinliğindedir.
Algoritma
- Kökü sütun 0 ve derinlik 0 ile ziyaret edin.
- Dizinin sonunu aşıyorsa veya
root[i]-1iseiindeksini atlayın. - Sütunda henüz bir düğüm yoksa veya bu derinlik kayıtlı olana eşit ya da daha büyükse, bu derinliği ve değeri kaydedin.
2i+1değerinicol-1sütunuyla, ardından2i+2değerinicol+1sütunuyla ziyaret edin; her ikisi de bir seviye daha derinde olsun.- Kaydedilen değerleri en küçük sütundan başlayarak döndürün.
def bottomView(root):
n = len(root)
best = {} # column -> (depth, value) of the deepest node found so far
def visit(i, col, depth):
if i >= n or root[i] == -1:
return
# Replace on a greater or equal depth: on a tie, the node
# met last is the one further right, which comes later in level order.
if col not in best or depth >= best[col][0]:
best[col] = (depth, root[i])
visit(2 * i + 1, col - 1, depth + 1)
visit(2 * i + 2, col + 1, depth + 1)
visit(0, 0, 0)
# The columns that hold a node form one unbroken range.
return [best[col][1] for col in range(min(best), max(best) + 1)]Genişlik öncelikli, her sütundaki son düğüm
Sezgi
Çıkan her düğümün önce sol çocuğunu, ardından sağ çocuğunu eklediği bir kuyruk, düğümleri seviye sırasıyla verir: d derinliğindeki her düğüm, d+1 derinliğindeki herhangi bir düğümden önce gelir ve her seviyede soldan sağa ilerlenir. Bir sütundaki düğümler arasında en derindeki en son çıkar; derinlikler eşitse daha sağdaki çıkar. Böylece her düğüm kendi sütununun yuvasındaki değerin üzerine yazdığında, her yuvada derinlikleri karşılaştırmaya gerek kalmadan alttan görülen düğüm kalır.
1. örnekte, 7 0. sütuna yazar ve 1 onun üzerine yazar.
Her düğüm için bir kuyruk ziyareti ve bir harita yazma işlemi gerekir: zaman O(n). Kuyruk, yaklaşık düğümlerin yarısı kadar olan tüm bir seviyeyi tutabilir; dolayısıyla alan O(n) olur.
Algoritma
- (indeks 0, sütun 0) çiftini bir kuyruğa koyun.
- Bir (
i,col) çiftini çıkarın veroot[i]değerinicolaltında saklayarak önceki değeri değiştirin. - Dizinin içinde olan ve
-1olmayan her çocuk için önce (2i+1,col-1), ardından (2i+2,col+1) çiftini ekleyin. - En küçük ve en büyük sütunu takip ederek kuyruk boşalana kadar tekrarlayın.
- Haritanın değerlerini, en küçük sütundan başlayarak döndürün.
from collections import deque
def bottomView(root):
n = len(root)
bottom = {} # column -> value of the last node seen in that column
queue = deque([(0, 0)]) # (node index, column); the root is never empty
while queue:
i, col = queue.popleft()
# The queue hands out deeper nodes later, and right after left
# on one level, so the last node to reach a column is the one seen from below.
bottom[col] = root[i]
left, right = 2 * i + 1, 2 * i + 2
if left < n and root[left] != -1:
queue.append((left, col - 1))
if right < n and root[right] != -1:
queue.append((right, col + 1))
# The columns that hold a node form one unbroken range.
return [bottom[col] for col in range(min(bottom), max(bottom) + 1)]
Tuzaklar ve uç durumlar
- Derinlik öncelikli sürümde yalnızca derinlik kesin olarak daha büyük olduğunda değiştirmek. Örnek 1'de bu nedenle
7,1yerine kalır. - Genişlik öncelikli aramada her sütun için ilk düğümü tutmak. Bu, üstten görünümü verir.
- Sağ çocuğu kuyruğa sol çocuktan önce eklemek. Böylece her seviye sağdan sola çıkar ve eşitliklerde yanlış düğüm seçilir.
- Yaprakları yanıt olarak almak. Örnek 1'de
7yaprağı1tarafından gizlenir ve örnek 2'de4düğümünün bir çocuğu olmasına rağmen 0. sütunun en altındadır. - Sütunları metin olarak sıralamak. Dize olarak
"-10","-1"ile"-2"arasına düşer.
Sıkça sorulan sorular3
İkili ağacın alt görünümü nedir?
Kök sütuna 0 verin, her sola adımda sütun numarasını bir azaltın ve her sağa adımda bir artırın. Alttan görünüm, soldan sağa her sütunun en derin düğümünü listeler. Bu problem, derinlik eşitliğini seviye sırasına göre çözer ve daha sonraki düğümü tutar.
İkili ağacın alt görünümünün zaman karmaşıklığı nedir?
n düğüm için O(n): genişlik öncelikli arama her düğümü bir kez işler ve bir hash map yazma işlemi yapar. Ağaç haritası gibi sıralı bir harita, w sütun için log w çarpanı ekler.
Üstten görünüm ile alttan görünüm arasındaki fark nedir?
İkisi de her sütundan bir düğüm seçer. Üstten görünüm en sığ düğümü, alttan görünüm ise en derin düğümü seçer. Genişlik öncelikli sürümde üstten görünüm, bir sütunun aldığı ilk değeri korur; alttan görünüm ise bu değeri her seferinde üzerine yazar.
Benzer problemler
Aynı fikirleri kullanan problemler. İki üçünü çözmek bir kalıbı kalıcı hale getirir.
def bottomView(root):
# Kodu buraya yazınTest #1
Test #2
Test #3
Argüman
root = [5, 2, 9, 4, 7, 1, 6]
Beklenen Çıktı
[4, 2, 1, 9, 6]