{"id":4698,"date":"2012-06-21T17:46:31","date_gmt":"2012-06-21T21:46:31","guid":{"rendered":"http:\/\/cscircles.cemc.uwaterloo.ca\/?page_id=4698"},"modified":"2018-10-28T19:48:38","modified_gmt":"2018-10-28T23:48:38","slug":"18-fr","status":"publish","type":"page","link":"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/18-fr\/","title":{"rendered":"18: Efficacit\u00e9"},"content":{"rendered":"<!-- Please retain this notice and add more notes if you create a new version.<br \/>\nMain French translator: Brice Canvel, brice.canvel@gmail.com<br \/>\nOriginal lesson author: David Pritchard, daveagp@gmail.com<br \/>\nLicense: http:\/\/creativecommons.org\/licenses\/by-nc-sa\/3.0\/<br \/>\nFor the full site, visit http:\/\/cscircles.ca-->\n<p>De nombreuses t\u00e2ches de programmation peuvent se faire de plusieurs fa\u00e7ons, mais l'une de ces fa\u00e7ons peut \u00eatre plus rapide qu'une autre. Concevoir des programmes rapides fait partie de l'art et de la science de la programmation informatique. Nous regardons quelques exemples dans cet exercice.<\/p>\n<h1>Partie 1: Ne pas recalculer la m\u00eame chose deux fois<\/h1>\n<p>La <a href=\"http:\/\/fr.wikipedia.org\/wiki\/Suite_de_Fibonacci\">suite de Fibonacci<\/a> est une s\u00e9quence simple et fascinante de nombres. Vous commencez avec deux nombres, 1 et 1. Ensuite, la r\u00e8gle est : <em>pour obtenir le nombre suivant, ajouter les deux pr\u00e9c\u00e9dents<\/em>. Par cons\u00e9quent, le prochain nombre est 1 + 1 = 2. Cela donne les trois premiers termes,<\/p>\n<p style=\"text-align: center;\"><code>1, 1, 2<\/code><\/p>\n<p>et le quatri\u00e8me terme est 1 + 2 = 3, alors nous avons 2 + 3 = 5, et ainsi de suite:<\/p>\n<p style=\"text-align: center;\"><code>1, 1, 2, 3, 5, 8, 13, ...<\/code><\/p>\n<p>La suite de Fibonacci a \u00e9t\u00e9 invent\u00e9e pour parler de populations de lapins, et elle a aussi \u00e9t\u00e9 reli\u00e9e \u00e0 l'architecture des plantes. Voici un extrait d'une s\u00e9rie vid\u00e9o (en anglais) impressionnante sur les nombres de Fibonacci: <div style='text-align: center;'>\n<iframe width='560' height='315' src='https:\/\/www.youtube.com\/embed\/ahXIMUkSXX0?rel=0' frameborder='0' allowfullscreen>\n<\/iframe>\n<\/div>\n<p>La d\u00e9finition des nombres de Fibonacci se pr\u00eate naturellement \u00e0 une fonction r\u00e9cursive. Le prochain exercice d\u00e9finit une fonction <code>Fibonacci(n)<\/code> pour donner le <code>n<\/code>i\u00e8me terme dans la liste ci-dessus (\u00e0 partir de <code>n = 1<\/code>).<\/p>\n<p><form class=\"pbform\" action=\"#\" id=\"pbform0\" method=\"POST\">\n<div class='pybox modeNeutral scramble' id='pybox0'>\n<img title='You have not yet completed this problem.' src='https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-content\/plugins\/pybox\/files\/icon.png' class='pycheck'\/><div class=\"heading\"><span class='type'>Scramble Exercise: <\/span><span class='title'>Nibofacci<\/span><\/div>D\u00e9chiffrez ce programme qui donne une d\u00e9finition r\u00e9cursive des nombres de Fibonacci. Les dix premiers d'entre eux seront affich\u00e9s.<ul class=\"pyscramble\" name=\"pyscramble\" id=\"pyscramble0\">\n <li class=\"pyscramble\">def Fibonacci(n):<\/li>\n <li class=\"pyscramble\">    else:<\/li>\n <li class=\"pyscramble\">        return 1<\/li>\n <li class=\"pyscramble\">    if (n==1 or n==2):<\/li>\n <li class=\"pyscramble\">        return Fibonacci(n-1) + Fibonacci(n-2)<\/li>\n<\/ul>\n<input type='hidden' id='usercode0' name='usercode0'\/>\n<div id='pbhistory0' class='flexcontain' style='display:none;'><\/div>\n<div name=\"pyinput\" id=\"pyinput0\">Enter testing statements like <code>print(myfunction(\"test argument\"))<\/code> below.<div class=\"pyboxTextwrap resizy\" style=\"height: 102px;\" ><textarea wrap=\"off\" name=\"userinput\" class=\"pyboxInput\" cols=10 rows=4><\/textarea><\/div><\/div>\n<div class='pyboxbuttons'><table><tr>\n<td><input type='submit' name='submit' id='submit0' value=' '\/><\/td>\n<td><input type='button' name='switch' id=\"switch0\" value=\"Input Switch\" onclick=\"pbInputSwitch(0,'Y')\" ><\/td>\n<\/tr><\/table><\/div>\n<input type=\"hidden\" name=\"lang\" value=\"\"\/><input type=\"hidden\" id=\"inputInUse0\" name=\"inputInUse\" value=\"Y\"\/>\n<input type=\"hidden\" name=\"pyId\" value=\"0\"\/>\n<input type=\"hidden\" name=\"hash\" value=\"b4c3f1d22dcd0c38bf02ab4dc059308a\"\/>\n<div id='pbresults0' class='pbresults'><\/div>\n<\/div>\n<\/form>\n<script type='text\/javascript'>pbInputSwitch(0,\"Y\");<\/script>\n<\/p>\n<p>Cependant, cette fonction r\u00e9cursive devient trop lente pour calculer les termes suivants de la suite. Appuyez sur<strong> Entrez instructions de test<\/strong>\u00a0et taper <code>print(Fibonacci(80))<\/code>. Lorsque vous testez, vous obtenez \"Time Limit Exceeded\" (d\u00e9lai maximal d\u00e9pass\u00e9).<\/p>\n<p>Pourquoi est-ce que \u00e7a va si lentement? La fonction n'a ni instruction complexe, ni boucle, juste une addition. Mais la lenteur s'av\u00e8re \u00eatre li\u00e9e au nombre d'appels totaux pour la fonction. Si nous appelons <code>Fibonacci(3)<\/code>, la fonction r\u00e9cursive est appel\u00e9e trois fois au total: l'appel initial, puis deux appels r\u00e9cursifs. Si nous appelons <code>Fibonacci(4)<\/code>, la fonction r\u00e9cursive est appel\u00e9e \u00e0 cinq reprises: l'appel initial, les trois fois dont nous venons de parler pour <code>n = 3<\/code>, et un appel r\u00e9cursif de plus pour <code>n = 2<\/code>. Calculer <code>Fibonacci(5)<\/code> g\u00e9n\u00e8re un total de neuf appels, et <code>Fibonacci(6)<\/code> g\u00e9n\u00e8re un total de 9 + 5 + 1 = 15 appels. Le nombre d'appels devient vite tr\u00e8s grand quand <code>n<\/code> grandit!<\/p>\n<p>En premi\u00e8re approximation, <code>Fibonacci(n+2)<\/code> n\u00e9cessite au moins deux fois plus d'appels que tous les appels r\u00e9cursifs de <code>Fibonacci(n)<\/code>, puisque <code>Fibonacci(n+2)<\/code> appelle <code>Fibonacci(n)<\/code> une fois directement et indirectement par l'interm\u00e9diaire de l'appel r\u00e9cursif \u00e0 <code>Fibonacci(n+1)<\/code>. De sorte que le temps de calcul est proportionnel \u00e0 une fonction <em>exponentielle<\/em> au moins aussi grande que (\u221a 2)<sup>n<\/sup>. C'est trop lent! Par exemple, <code>Fibonacci(80)<\/code> n\u00e9cessite plus de 2<sup>40<\/sup>=1099511627776 appels r\u00e9cursifs.<\/p>\n<p>Ce raisonnement met en \u00e9vidence le probl\u00e8me conceptuel sous-jacent : l'appel \u00e0 <code>Fibonacci(n)<\/code> se fait \u00e0 deux reprises et le recalcul du r\u00e9sultat \u00e0 partir du d\u00e9but la deuxi\u00e8me fois est un gaspillage. Nous devrions arriver \u00e0 une approche o\u00f9 l'on ne perd pas de temps \u00e0 recalculer la m\u00eame chose encore et encore.<\/p>\n<h2>La solution<\/h2>\n<p>Essayons de faire quelque chose en Python plus semblable \u00e0 l'introduction. Nous avons commenc\u00e9 par \u00e9crire 1, 1. Puis nous avons continu\u00e9 \u00e0 \u00e9tendre la s\u00e9quence en ajoutant les deux derniers \u00e9l\u00e9ments.\u00a0Un tel programme est donn\u00e9 ci-dessous, mais vous devez le d\u00e9chiffrer.<\/p>\n<p><form class=\"pbform\" action=\"#\" id=\"pbform1\" method=\"POST\">\n<div class='pybox modeNeutral scramble' id='pybox1'>\n<img title='You have not yet completed this problem.' src='https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-content\/plugins\/pybox\/files\/icon.png' class='pycheck'\/><div class=\"heading\"><span class='type'>Scramble Exercise: <\/span><span class='title'>Fibonacci rapide<\/span><\/div>D\u00e9chiffrez ce programme de calcul rapide de la suite de Fibonacci.<ul class=\"pyscramble\" name=\"pyscramble\" id=\"pyscramble1\">\n <li class=\"pyscramble\">    for i in range(3, n+1):      <\/li>\n <li class=\"pyscramble\">    suite = [0, 1, 1]  # Fibonacci(0) est 0, Fibonacci(1) and Fibonacci(2) sont 1<\/li>\n <li class=\"pyscramble\">        suite.append(suite[i-1] + suite[i-2])<\/li>\n <li class=\"pyscramble\">def Fibonacci(n):<\/li>\n <li class=\"pyscramble\">    return suite[n]<\/li>\n<\/ul>\n<input type='hidden' id='usercode1' name='usercode1'\/>\n<div id='pbhistory1' class='flexcontain' style='display:none;'><\/div>\n<div name=\"pyinput\" id=\"pyinput1\">Enter testing statements like <code>print(myfunction(\"test argument\"))<\/code> below.<div class=\"pyboxTextwrap resizy\" style=\"height: 102px;\" ><textarea wrap=\"off\" name=\"userinput\" class=\"pyboxInput\" cols=10 rows=4><\/textarea><\/div><\/div>\n<div class='pyboxbuttons'><table><tr>\n<td><input type='submit' name='submit' id='submit1' value=' '\/><\/td>\n<td><input type='button' name='switch' id=\"switch1\" value=\"Input Switch\" onclick=\"pbInputSwitch(1,'Y')\" ><\/td>\n<\/tr><\/table><\/div>\n<input type=\"hidden\" name=\"lang\" value=\"\"\/><input type=\"hidden\" id=\"inputInUse1\" name=\"inputInUse\" value=\"Y\"\/>\n<input type=\"hidden\" name=\"pyId\" value=\"1\"\/>\n<input type=\"hidden\" name=\"hash\" value=\"2dd50162e4af080e714d6ff07ab0fd81\"\/>\n<div id='pbresults1' class='pbresults'><\/div>\n<\/div>\n<\/form>\n<script type='text\/javascript'>pbInputSwitch(1,\"Y\");<\/script>\n<\/p>\n<p>Il y a encore des possibilit\u00e9s d'am\u00e9lioration, puisque nous n'avons pas besoin de recalculer la totalit\u00e9 du tableau \u00e0 chaque nouvel appel, mais la solution est d\u00e9j\u00e0 correcte, car elle fonctionne rapidement, m\u00eame sur les grandes valeurs de n!<\/p>\n<h1>Partie 2: Ne calculez pas des choses inutiles, m\u00eame une seule fois<\/h1>\n<p>Notre second exemple concerne la v\u00e9rification pour un nombre du fait qu'il soit <strong>premier<\/strong>, ce qui est important en cryptographie, donc au niveau de la s\u00e9curit\u00e9 informatique. Un nombre est premier s'il a uniquement deux diviseurs distincts: 1 et lui-m\u00eame. Les premiers nombres premiers sont 2, 3, 5, 7, 11, 13, 17, 19, 23. (Par exemple, 21 n'est pas premier car 3 et 7 sont des diviseurs, en plus de 1 et 21.)<\/p>\n<p>Comment peut-on v\u00e9rifier si un nombre est premier en Python? Nous avons vu <a href=\"\/7b-fr\/\">plus t\u00f4t<\/a> comment tester la divisibilit\u00e9 :<\/p>\n<p style=\"text-align: center;\"><code>N % D == 0 \u00a0# a la valeur True si D est un diviseur de N, et False sinon<\/code><\/p>\n<p>Donc, en testant tous les diviseurs possibles, nous arrivons au programme suivant.<\/p>\n<p><form class=\"pbform\" action=\"#\" id=\"pbform2\" method=\"POST\">\n<div class='pybox modeNeutral  facultative' id='pybox2'>\n<div class=\"heading\"><span class=\"title\">Example<\/span><\/div>Test si quelques nombres sont premiers<div class='pyboxTextwrap pyboxCodewrap RO '  style='height: 162px;'><textarea wrap='off' name='usercode2' id='usercode2'  cols=10 rows=6 readonly='readonly'  style = 'height : 162px;'  class='pyboxCode RO'>\ndef testePremier(N):\n  for D in range(2, N):                        # essai D de 2 \u00e0 N-1\n    if N % D == 0:                             # D divise-t-il N?\n      print(N, \"n'est pas premier; divisible par\", D)\n      return\n  print(N, \"est premier\")                      # rien diviseurs trouve<\/textarea><\/div>\n<div id='pbhistory2' class='flexcontain' style='display:none;'><\/div>\n<div name=\"pyinput\" id=\"pyinput2\">Enter testing statements like <code>print(myfunction(\"test argument\"))<\/code> below.<div class=\"pyboxTextwrap resizy\" style=\"height: 102px;\" ><textarea wrap=\"off\" name=\"userinput\" class=\"pyboxInput\" cols=10 rows=4><\/textarea><\/div><\/div>\n<div class='pyboxbuttons'><table><tr>\n<td><input type='submit' name='submit' id='submit2' value=' '\/><\/td>\n<td><input type='button' name='switch' id=\"switch2\" value=\"Input Switch\" onclick=\"pbInputSwitch(2,'Y')\" ><\/td>\n<td><input type='button' name='consolecopy' value=\"Open in console\" onclick=\"pbConsoleCopy(2)\" ><\/td>\n<td><input type='button' name='visualize' value=\"Visualize\" onclick=\"pbVisualize(2,'Y')\" ><\/td>\n<\/tr><\/table><\/div>\n<input type=\"hidden\" name=\"lang\" value=\"\"\/><input type=\"hidden\" id=\"inputInUse2\" name=\"inputInUse\" value=\"Y\"\/>\n<input type=\"hidden\" name=\"pyId\" value=\"2\"\/>\n<input type=\"hidden\" name=\"hash\" value=\"56b60ddd88f92fb25bb1ffacab26ee2d\"\/>\n<div id='pbresults2' class='pbresults'><\/div>\n<\/div>\n<\/form>\n<script type='text\/javascript'>pbInputSwitch(2,\"Y\");<\/script>\n<\/p>\n<p>Il fonctionne! Mais il est h\u00e9las trop lent pour un grand nombre. <strong>Tape entr\u00e9e<\/strong> et taper <code>testePremier(324635459)<\/code>. Il d\u00e9passe les limites en temps. Essayez avec quelques valeurs : pour des nombres premiers sup\u00e9rieurs \u00e0 environ 10000000 le code provoque toujours un d\u00e9passement de temps de calcul, car la boucle de v\u00e9rification de la divisibilit\u00e9 s'ex\u00e9cute seulement environ 10 millions de fois par seconde. Si nous voulons v\u00e9rifier des nombres plus grand encore, nous aurons besoin d'une id\u00e9e plus efficace. Mais voyez que le code fonctionne \u00e9galement pour <em>quelques<\/em> grands nombres\u00a0 comme un billion (1000000000000)!<\/p>\n<p>Avons-nous vraiment besoin de v\u00e9rifier <strong>tous<\/strong> les nombres compris entre <code>2<\/code> et <code>N-1<\/code>, pour v\u00e9rifier si <code>N<\/code> est premier? <a class=\"hintlink\"  id=\"hintlink3\">Indice<\/a><\/p>\n<h2>L'id\u00e9e, et un argument<\/h2>\n<p>Si vous lisez la suggestion et exp\u00e9rimentez, vous remarquez sans doute que lorsque <code>N<\/code> n'est pas premier, le programme trouve habituellement un facteur tr\u00e8s faible par rapport \u00e0 <code>N<\/code>. Par exemple, <code>testePremier(34827948723948723984729834)<\/code> fonctionne assez rapidement, m\u00eame si son entr\u00e9e est gigantesque, puisque trouver le diviseur <code>D = 2<\/code> est imm\u00e9diat.<\/p>\n<p>Peut-\u00eatre que nous n'avons pas vraiment besoin de v\u00e9rifier tous les facteurs possibles. Y aurait-il une limite au plus petit nombre de facteurs \u00e0 v\u00e9rifier, avant que nous puissions \u00eatre s\u00fbrs que <code>N<\/code> est un nombre premier ? Heureusement, oui! En fait, on peut dire que <em>si <code>N<\/code> n'est pas premier, l'un de ses diviseurs est au plus <code>sqrt(N)<\/code><\/em>. Pourquoi cela? Eh bien, si <code>N<\/code> n'est pas premier, alors il a un diviseur <code>A<\/code>. Avoir un diviseur signifie qu'il y a un autre nombre <code>B<\/code> tel que :<\/p>\n<p style=\"text-align: center;\"><code>A * B == N<\/code><\/p>\n<p>Maintenant, si <code>A<\/code> \u2264<code>sqrt(N)<\/code> ou <code>B<\/code> \u2264 <code>sqrt(N)<\/code> , alors nous sommes heureux: nous avons trouv\u00e9 un facteur de <code>N<\/code> qui est petit, comme nous le voulions. Mais en r\u00e9alit\u00e9, ce sont les seules possibilit\u00e9s. Supposons l'inverse, nous obtenons alors la contradiction :<\/p>\n<p style=\"text-align: center;\"><code>N = A * B &gt; sqrt(N) * sqrt(N) = N<\/code><\/p>\n<p>ce qui est impossible.<br \/>\nSuper! Alors maintenant, nous allons mettre en \u0153uvre en Python cette nouvelle id\u00e9e. La meilleure fa\u00e7on de changer l'ancienne approche est d'ajouter un test dans la boucle <code>for<\/code> : une fois <code>D &gt; sqrt(N)<\/code> (ou de mani\u00e8re \u00e9quivalente <code>D * D &gt; N<\/code>), nous pouvons simplement sortir de la boucle par un <code>break<\/code> et interrompre les essais.<\/p>\n<p><form class=\"pbform\" action=\"#\" id=\"pbform4\" method=\"POST\">\n<div class='pybox modeNeutral  facultative' id='pybox4'>\n<div class=\"heading\"><span class=\"title\">Example<\/span><\/div>Test rapide de d\u00e9tection rapide d'un nombre premier<div class='pyboxTextwrap pyboxCodewrap RO '  style='height: 292px;'><textarea wrap='off' name='usercode4' id='usercode4'  cols=10 rows=11 readonly='readonly'  style = 'height : 292px;'  class='pyboxCode RO'>\ndef testePremier(N):\n  for D in range(2, N):                        \n    if (D * D > N):          # premi\u00e8re ligne nouvelle\n      break                  # deuxi\u00e8me ligne nouvelle\n    if N % D == 0:                             \n      print(N, \"n'est pas premier; divisible par\", D)\n      return\n  print(N, \"est premier\")                      \n\ntestePremier(1000006000009)\ntestePremier(1666666009999)<\/textarea><\/div>\n<div id='pbhistory4' class='flexcontain' style='display:none;'><\/div>\n<div class='pyboxbuttons'><table><tr>\n<td><input type='submit' name='submit' id='submit4' value=' '\/><\/td>\n<td><input type='button' name='consolecopy' value=\"Open in console\" onclick=\"pbConsoleCopy(4)\" ><\/td>\n<td><input type='button' name='visualize' value=\"Visualize\" onclick=\"pbVisualize(4,'N')\" ><\/td>\n<\/tr><\/table><\/div>\n<input type=\"hidden\" name=\"lang\" value=\"\"\/><input type=\"hidden\" id=\"inputInUse4\" name=\"inputInUse\" value=\"Y\"\/>\n<input type=\"hidden\" name=\"pyId\" value=\"4\"\/>\n<input type=\"hidden\" name=\"hash\" value=\"f600bbeca08c5adade01abdeecb1326e\"\/>\n<div id='pbresults4' class='pbresults'><\/div>\n<\/div>\n<\/form>\n<script type='text\/javascript'>document.getElementById(\"submit4\").value = \"Run program\";document.getElementById(\"inputInUse4\").value = \"N\";<\/script>\n<\/p>\n<p>Le programme fonctionne maintenant sur les nombres premiers gigantesques!<\/p>\n<h2>Exercice final<\/h2>\n<p>Dans cet exercice, nous combinons le calcul sur les nombres premiers de la seconde moiti\u00e9 de cette le\u00e7on avec l'approche fond\u00e9e sur une liste de la premi\u00e8re moiti\u00e9. Ici le code doit remplir un tableau de longueur 1000001 afin que <code>estPremier[N]<\/code> prenne la valeur <code>True<\/code> si <code>N<\/code> est un nombre premier, et <code>False<\/code> sinon, pour tout <code>N<\/code> jusqu'\u00e0 un million (<code>estPremier[0]<\/code> et <code>estPremier[1]<\/code>\u00a0doivent\u00a0\u00eatre\u00a0<code>False<\/code>, par convention).<\/p>\n<p><a class=\"hintlink\"  id=\"hintlink5\"> Cliquez ici pour un indice. C'est un gros! <\/a><\/p>\n<p><form class=\"pbform\" action=\"#\" id=\"pbform6\" method=\"POST\">\n<div class='pybox modeNeutral ' id='pybox6'>\n<img title='You have not yet completed this problem.' src='https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-content\/plugins\/pybox\/files\/icon.png' class='pycheck'\/><div class=\"heading\"><span class='type'>Coding Exercise: <\/span><span class='title'>Quand les nombres premiers d\u00e9collent<\/span><\/div> \u00c9crire un programme qui d\u00e9finit la table <code>estPremier<\/code>, d\u00e9crite ci-dessus. <a class=\"hintlink\"  id=\"hintlink7\">Suggestion<\/a> <br\/> <em>Le classeur permet un temps d'ex\u00e9cution plus long que normal, <strong>7 secondes<\/strong>, pour qu'il n'y ait pas de d\u00e9passement de temps de calcul.<\/em><div class=\"helpOuter\" style=\"display: none;\"><div class=\"helpInner\"><div style=\"text-align: center\">You need to create an account and log in to ask a question.<\/div><\/div><\/div><div class='pyboxTextwrap pyboxCodewrap RW resizy'  style='height: 526px;'><textarea wrap='off' name='usercode6' id='usercode6'  cols=10 rows=20   class='pyboxCode RW'>\n# delete this comment and enter your code here\n<\/textarea><\/div>\n<div id='pbhistory6' class='flexcontain' style='display:none;'><\/div>\n<div name=\"pyinput\" id=\"pyinput6\">Enter testing statements like <code>print(myfunction(\"test argument\"))<\/code> below.<div class=\"pyboxTextwrap resizy\" style=\"height: 102px;\" ><textarea wrap=\"off\" name=\"userinput\" class=\"pyboxInput\" cols=10 rows=4><\/textarea><\/div><\/div>\n<div class='pyboxbuttons'><table><tr>\n<td><input type='submit' name='submit' id='submit6' value=' '\/><\/td>\n<td><input type='button' name='switch' id=\"switch6\" value=\"Input Switch\" onclick=\"pbInputSwitch(6,'Y')\" ><\/td>\n<td><input type='button' name='consolecopy' value=\"Open in console\" onclick=\"pbConsoleCopy(6)\" ><\/td>\n<td><input type='button' name='visualize' value=\"Visualize\" onclick=\"pbVisualize(6,'Y')\" ><\/td>\n<\/tr><\/table><select id='pbSelect6' class='selectmore'><option name='more'>More actions...<\/option>\n<option name='history' data-pbonclick=\"historyClick(6,'18.sieve')\" >History<\/option>\n<option name='help' data-pbonclick=\"helpClick(6);\" >Help<\/option>\n<\/select><\/div>\n<input type='hidden' name='timeout' value='20000'\/>\n<input type=\"hidden\" name=\"lang\" value=\"\"\/><input type=\"hidden\" id=\"inputInUse6\" name=\"inputInUse\" value=\"Y\"\/>\n<input type=\"hidden\" name=\"pyId\" value=\"6\"\/>\n<input type=\"hidden\" name=\"hash\" value=\"3e58317b5d378dd273ab85573cd5fdfb\"\/>\n<div id='pbresults6' class='pbresults avoidline'><\/div>\n<\/div>\n<\/form>\n<script type='text\/javascript'>jQuery(function(){pbToggleCodeMirror(6);});pbInputSwitch(6,\"Y\");<\/script>\n<\/p>\n<p><table class='pywarn'><tr><td class='pywarnleft'><img src='https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-content\/plugins\/pybox\/files\/warning.png'\/><\/td><td class='pywarnright'><span>  Ceci est le dernier exercice du site Web \u00abCercles Informatiques\u00bb. F\u00e9licitations \u00e0 ceux qui ont essay\u00e9 toutes les le\u00e7ons! Voir la <a class=\"open-same-window\" href=\"\/ressources\/\">page de ressources<\/a> pour avoir des suggestions sur ce qu'il faut apprendre par la suite. Amusez-vous bien, bonne chance, et bon codage ! <\/span><\/td><\/table><\/p>\n","protected":false},"excerpt":{"rendered":"<p>De nombreuses t\u00e2ches de programmation peuvent se faire de plusieurs fa\u00e7ons, mais l'une de ces fa\u00e7ons peut \u00eatre plus rapide qu'une autre. Concevoir des programmes rapides fait partie de l'art et de la science de la programmation informatique. Nous regardons &hellip; <a href=\"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/18-fr\/\">Continue reading <span class=\"meta-nav\">&rarr;<\/span><\/a><\/p>\n","protected":false},"author":1,"featured_media":0,"parent":0,"menu_order":0,"comment_status":"closed","ping_status":"closed","template":"","meta":{"footnotes":""},"class_list":["post-4698","page","type-page","status-publish","hentry"],"_links":{"self":[{"href":"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-json\/wp\/v2\/pages\/4698","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-json\/wp\/v2\/pages"}],"about":[{"href":"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-json\/wp\/v2\/types\/page"}],"author":[{"embeddable":true,"href":"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-json\/wp\/v2\/users\/1"}],"replies":[{"embeddable":true,"href":"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-json\/wp\/v2\/comments?post=4698"}],"version-history":[{"count":40,"href":"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-json\/wp\/v2\/pages\/4698\/revisions"}],"predecessor-version":[{"id":11089,"href":"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-json\/wp\/v2\/pages\/4698\/revisions\/11089"}],"wp:attachment":[{"href":"https:\/\/cscircles.cemc.uwaterloo.ca\/dev\/wp-json\/wp\/v2\/media?parent=4698"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}