Arbre binaire presque complet

On s'intéresse dans cet exercice aux arbres binaires presque complets. Un tel arbre binaire est soit :

  • un arbre vide ;

  • un arbre binaire dont tous les niveaux sont remplis à l'exception éventuelle du dernier qui, s'il n'est pas entièrement rempli, est « tassé » à gauche : tous les nœuds présents au dernier niveau se trouvent sur la gauche de l'arbre binaire.

Un arbre binaire presque complet

flowchart TD
    a((a)) --> b((b))
    a      --> c((c))
    b      --> d((d))
    b      --> e((e))
    c      --> f((f))
    c      ~~~ g(( ))
    style g fill:none,stroke:none,color:none
    classDef noeud font-family:consolas;
    class a,b,c,d,e,f noeud;

On n'a pas représenté les arbres binaires vides.

Cet arbre binaire est presque complet : les deux premiers niveaux sont entièrement remplis, les nœuds du dernier niveau se trouvent sur la gauche.

Un arbre binaire presque complet de taille \(n\) peut être représenté en machine par un tableau de \(n+1\) valeurs. En indexant les valeurs à partir de \(0\), on trouve :

  • une valeur quelconque à l'indice \(0\) ;
  • la valeur portée par la racine à l'indice \(1\).

Pour les autres nœuds, on considère les règles suivantes. Si la valeur d'un nœud est stockée à l'indice \(k\) :

  • si son sous-arbre gauche est non-vide, sa valeur est stockée à l'indice \(2k\) ;
  • si son sous-arbre droit est non-vide, sa valeur est stockée à l'indice \(2k+1\).

Avec Python, on peut donc représenter les arbres binaires presque complets à l'aide de listes. On place la valeur None à l'indice 0.

L'arbre vide est donc représenté par la liste [None].

Représentation de l'arbre binaire vu plus haut

L'arbre binaire dessiné plus haut a une taille de \(6\). Il est donc représenté par une liste de longueur 7 :

# indices   0   1    2    3    4    5    6
arbre = [None, 'a', 'b', 'c', 'd', 'e', 'f']

Le 'b' se trouve a l'indice 2. On trouve bien 'd' à l'indice 2*2 = 4 et 'e' à l'indice 2*2 + 1 = 5.

1. Taille de l'arbre binaire

Écrire la fonction taille qui prend en paramètre une liste représentant un arbre binaire presque complet et renvoie sa taille.

Exemples
>>> taille([None])
0
>>> taille([None, 'a', 'b', 'c', 'd', 'e', 'f'])
6

###(Dés-)Active le code après la ligne # Tests (insensible à la casse)
(Ctrl+I)
Entrer ou sortir du mode "deux colonnes"
(Alt+: ; Ctrl pour inverser les colonnes)
Entrer ou sortir du mode "plein écran"
(Esc)
Tronquer ou non le feedback dans les terminaux (sortie standard & stacktrace / relancer le code pour appliquer)
Si activé, le texte copié dans le terminal est joint sur une seule ligne avant d'être copié dans le presse-papier
Évaluations restantes : 10/10

.339.128013beqOn,évi3mo_txR;Ph}klpw!f(: cg.a=ry0S-u/{2)As1^d050Y0d0p0I0k0x0V0E0F0x0I0V0V0J010p0k0y010406050V0P0m0m0I0K0L040N0n0x0P0?0n0g0E020I0m0y0s0E0r0d100K0e0P0d0V050Q0}0 11130{0y04051y1r1B0Q1y0{0Y0k0j0+0-0/0;0u0k0G0u0x1P0u0p0_050$0c0x0d1K0.0:011O1Q1S1Q0p1Y1!1W0p0K1z0p0u0+160V0y0I0g0;0S011$1M010B0(0d0g1e0d1W1|1~231(261!290m2b040b0E0t0K0n0y0n0V0k191b0!1`0K0K0d0F2w1r2d0g1z0Q1^2I1=1@1?1X0Y2f0;1S0g282t1W1H1J0,1%2S0k2U0g0n2Y1W0y2B1z2G2I2:0|1}1b2!242)0K100x0_0W2F2@0`2?2e2_1(2{2}0_0S311~2I2-0d2I2Y2L0Y1@2Q360;0F2*2l0Z1I1z3f2/323c2H053p0!3w351L1(0w0_0!0B3y3D2^3F0;0z0_0E3L343N2#010g0B0_0$0(1!3T2G2R010^040C3(2@3*0g0_110c2B3/3E3W3,0T0D3L060E423S3)3n013H042B0p0P0K0g3L443:460g0c0_2i3`3V243,3.1s3x453O3X3?0K3^0d4n3*3}4f3U3*0n0_0O4E4u3W0m0k2 401r3B3g1C2.1r3i1r0p3k4Y2O2J0I1Z4T0Q3i1x3M3*2B0m0o0B0I0w0d0o0u0l0_1j1l1n1p0E3 4s3d1C331y0f1b2)0p0d0K0I0E500h0E0Y1~0*1!0+0.0E2-0i0F0k0*2y0F0#5c0E2B5r0V280$2w5j513@2B0*0c2%0%5K5q5K501`1f1!0p0V5i1a5q0d185j1a0F0E0n0c5c0g0k0K0E0-0E3#0x5n2y0x005J1#280E2U0E4?5u1~0p5g0P000P610V0n0P0V1=0I2D0k5Z0D3S4S3*1*1R1T1V4.4i4k044m543z4L4p0_4r2=6A374x4z4B464D6y044g3{244H044J6M6O4o1(4N4P6M4R3q040H564-0U2%2u5;1#0F0I0x0F0P0x5H5;5f5@5_691b5}5T0y0$0g664F46112v0u105c0q0_090C0W0M0X0R7h0v090T4f0g0a0P0Y0*6b5d5f1}0*0y170*3p5U0k1n0i600k5;1a0G676/0d177J0Y6~0E700j0k2y0A6)4W0#0%0)04.
2. Hauteur de l'arbre binaire

Écrire la fonction hauteur qui prend en paramètre une liste représentant un arbre binaire presque complet et renvoie sa hauteur.

Une version valide de la fonction taille est disponible dans l'éditeur ci-dessous. Vous pouvez directement l'utiliser sans l'importer.

Exemples
>>> hauteur([None])
0
>>> hauteur([None, 'a', 'b', 'c', 'd', 'e', 'f'])
3

###(Dés-)Active le code après la ligne # Tests (insensible à la casse)
(Ctrl+I)
Entrer ou sortir du mode "deux colonnes"
(Alt+: ; Ctrl pour inverser les colonnes)
Entrer ou sortir du mode "plein écran"
(Esc)
Tronquer ou non le feedback dans les terminaux (sortie standard & stacktrace / relancer le code pour appliquer)
Si activé, le texte copié dans le terminal est joint sur une seule ligne avant d'être copié dans le presse-papier
Évaluations restantes : 10/10

.339.128013bqO,9vià3o_x;jlpw!f( g06-)2As1+8ené4èm5tLRPhk`:c.a=ryDS*u/7d050-0I0P0Z0i0q0E0w0X0q0Z0E0E0!010P0i0r010406050E0*0N0N0Z0#0$040(0l0q0*110l0J0w020Z0N0r0o0w0R0I1b0#0d0*0I0E050+181a1c1e160r04051J1C1M0+1J160-0i0h0_0{0}0 0T0i0x0T0q1!0T0P14050;0c0q0I1V0|0~011Z1#1%1#0P1-1/1+0P0#1K0P0T0_1h0E0r0Z0J0 0C011;1X010u0?0I0J1p0I1+27292e1?2h1/2k0N2m040b0w0S0#0l0r0l0E0i1k1m0/250#0#0I0X2H1C2o0J1K0+232T2022211,0-2q0 1%0J2j2E1+1S1U0`1=2%0i2)0J0l2-1+0r2M1K2R2T2~17281m2/2f2@0#1b0q140F2Q3215312p341?3638140C3c293e2R2$013j0Z39040k3n2S163q3h0 3t3v0L3y3p323r3E140O3H3A3J3C3s0l373u140z3O3f331W3i3T3k040,3Y3B3#3D3%3V040H3+3Q3-3S3U3v0g3H1N2|1C2-2W0-222#3R0X2^2w0.1T1K2{0I2}3d3}470/4f3g3^0U140/0u3}3,2:010s140w4r3@4t0J0u140T0Z1j0I0*0#4y4l4t13040v4K3!4A141c0c2M4Q3r4N0B0W3O0w4%4x4s2f4n040i4q1D3d4)4z350c142t4X3R4N4P4:3o3Z3K4T0#4V0I4{3^4Z3H4=4L2f0l140!0!5a513R0N0i3a574M144#4 3z4(5u5b4R4+142M0P4I0J5i4*1?5l140y4$4(5j3^0J140i5E4?1?5e045h5s045w3K4^044`5X5M5p4O5o3553555,1?595X5Z3R5U0A5R5c5G5m043b5X065u5)5-040P5{5x5T5f683r5H5 5K4%641?4,0s1Z1/6c3R5O4-6o3^5U0t5W2~5@3^6e60305F0 4N5r2~625v6h6D3s5P6s4t5U6w4;6i3D6N5?6T015U0+0+6O2f6e3m616J6K5S6U666$6a5V6:6.676W6L5U0G6?016A6g6y4t4,5A5C6}6q6^6H1C4i4e3~7c0+411C0P437h2Z2U0Z1.7e411I4k690 2M0N0m0u0Z0U0I0m0T0k141u1w1y1A0w6G4g1P3e1J0Q000i0-0K1:1A0P0w2J280#110#7Y0*0w0J0a0*2#1/0w0r1i0^0j7Y2B2G1:0-7)0/0#0J0i0I7%800h0I4F0w0v7+7-7Y7R0J1S0X1:057b3r1^1$1(1*7s526r6_6-6Y6b8s5|3D5#5%6C8t4}5:6.4U4W5(6L5=6x6X5_6}6 5(0+7b040B0w0:7Y1:7v1l0P820w7@0{0w0#0Z0X2=0I0Y2z0l4I0_1:7y0i2M0w1l7Y1T0i0E1:8g7X2=8f1:7!8X0*0n0w0p0*0E1y007@0Z1|0I958{0q8d968X0w8)8+8-2)0Y1N7O040e1m2D4I8+2G0w4F0}0i0f8%9s8d850#919L7!7$9r9t8,8.888(9p0i8g4x8j3R8l1`1)2n8t8P308R488T8V7X0/0E8g8e8{2J0E8=0E0A8G1:0x4F0X0T7V1ma09ea3548{a60*a88/0w0%290^9%0X0|8|1m4F9F7X5r1Q4a2.3^9+8n9.8x2g2i2u2w2y0(0X0#127X0S0$231l3}4d7s2 4g8S6X4,4p8E4u4wa%4B4D4F8#4Ia%8D8I8t6qa4a:144!706X776}6Q76140;0?6na=aFa;8BaFa@af56b67t018K3d6I6,ba4Da 8v8L6L6e5J6*5L6L6q5Q8wbfb0by6d5~6Bbi636L6k6mbdbpa?6VbLaF5U020q0P0o6R3o7165784g8J5q70bGbM8rbObzbo6Sbq5~6)b+3r5U0)b1b*bF6+a}bmbB5^b-bWb}040Tbn046|b 6zbDa|bH5z0:75c94Sc43Y9=4j7d2T7q1L040Q7J2-900i1l0^180X8g9J850^988i488k1(9,8o6X6(3}cl4e0w0K0h0l7I0J7X1/ao1l9P2Fcx8V1m0c2=0=2M8:0D2=2F9L2Fas250J2F0-0M9~7Ja40^2@0J0A0h7S1A9L8)4E4G8?0-000*atbc0wc*2k8`972M9f1z251q1/7X7W9s0i7U9H7)2@0N559rc*0PcE822v1|299_000KaMdk9s0Z0wb30q7/2J8g1i0i0A8-9x7N7rcs0^200l900w0u1l2Ocwc_0w181TdJ7Ja0cW7Yd/dx9J0w0h3ud50^ax3e0*0q3e1%9z2j0w1j0?90dJ9(cH9*cJaD8p6p5#dicOaZd$azcI1_en6X2s2j2l14aKdN0raPaR0TaT5(aV3ZaX50aZcd04a$be3r4v5Ya*4Cc4a-4H4JeU4|144~b9bfbb5/e(58a`7L3objbX3ib2c6bV2Se_6@0=dTbKb!8Ce*a*5.8He,4Ya`cc8t4,4.b_bZc26`5fe}eXb/5Ia_04e?5tb|eR747 8O5~bs6Hb(aF73cffxch4@4_2jfqe+f4baeq2=fLf76/e:5*0B0Bc65`fH5}3l5ae 010X0F1403dh2=0v0P8Udt2{0K2h0n0K7:1c0w0V0y0c0Vd}0J0Xc@ac0E200=7Xb;bi7a9?cn404b160+eb16glcqedef1%0EeicGdVaBem1{aEe-4_0l0xgc50cP5Ye61R1Tew8mgyeo3^eAaIeD0waLaNeG2zeIeK30eM9;30eQfe6q0u2B0Na%eW4xfU356q1b23g.a)g;6jbw1q3Tfie~c30qgCgE3z3PfD4o0I4/fa3Rg/eYa,dae%hce;5+g{8Fbcfqa{btbkgAfTb=c06=f!f0b4f350b#hlhjcia^hmbgfchrf(ffhbb.b)h0fn8t6Qfmf(brfqfs156+hMce5BfGhvcafphLa!h%cgh*4A5#2=hR6Xb8fNhth3gDfRhIa~hI4ZfXhy8uc7fy5n61gecm1P3 7fgi1Cgngn1J7;9e8|aN0xc+0q9L0Z85g5gu92gwexgNa}h?cWa%5Ud#hF65dD0m2t0xg^i2e*i49;8S0w1y0i8*2jcT819s1:dzdB2JdD0^dcdec(118$gIeveliz9-gO4tgQeC2xgTeFeHaS5DeL3 g$aYgfeReTiH1?hei0eZd9a.hih{fbhEjh6pf8hB2Sh_e=fdblhuhPbPc1h1bvb2f1b5j96Ef6i0jmhpjrbfhNfhe|hVcMfzhYb%bufeh/h)jubfhXh-fvfFj1h;bYiE14iGjk5N14iJiLiNjChJ4OiQgdgGggif0h3egk0ij~e8j~0/dS0E04.