# articles

feed_id: http://sametmax.com/?p=3505
title: Utiliser des UUID comme primary key avec l’ORM de Django
uri: Utiliser-des-UUID-comme-primary-key-avec-l-ORM-de-Django
url: http://sametmax.com/utiliser-des-uuid-comme-primary-key-avec-lorm-de-django/
content:
<p>Par défaut Django ajoute automatiquement un champ <code>id</code> à tous les modèles, et le configure pour être un entier qui s&#8217;auto incrémente puis le désigne comme la clé primaire. Il est néanmoins possible d&#8217;utiliser un autre champ comme clé primaire pour sa table: un <a href="http://sametmax.com/slug-dune-chaine-de-caracteres-non-ascii-avec-django-et-unidecode/">slug</a> ou un <a href="https://fr.wikipedia.org/wiki/Num%C3%A9ro_de_s%C3%A9curit%C3%A9_sociale_en_France">identifiant métier</a>. Dans notre cas, on va voir comment utiliser un <a href="https://fr.wikipedia.org/wiki/UUID">UUID</a>.</p>
<p>Un UUID est un identifiant généré de manière pseudo aléatoire qui a une forte probabilité d&#8217;être unique dans le monde entier, il y a 4&#215;10³⁷ combinaisons possibles pour les versions des algos récents. Selon le <a href="https://fr.wikipedia.org/wiki/Paradoxe_des_anniversaires">paradoxe des anniversaires</a>, il faudrait créer un milliard de UUID par seconde pendant 100 ans pour que le prochain ait 50% de chance d&#8217;être un doublon. Normalement pour votre site de fans club des limules hermaphrodites, ça devrait être suffisant.</p>
<p>Utiliser des UUID possède de <a href="http://www.codinghorror.com/blog/2007/03/primary-keys-ids-versus-guids.html">nombreux avantages</a> car ils sont plus ou moins garantis d&#8217;être uniques, et ainsi:</p>
<ul>
<li>Vos serveurs peuvent les générer indépendemment les uns des autres.</li>
<li>.<code>/manage.py loadata</code> ne va pas vous crasher à la gueule à cause d&#8217;une duplicate key.</li>
<li>On peut faire du <a href="http://en.wikipedia.org/wiki/Shard_%28database_architecture%29">sharding</a> sur la clé très facilement.</li>
<li>Faire des réplications et des synchronisations est beaucoup plus simple qu&#8217;avec un <code>AUTO INT</code>.</li>
<li>Votre modèle n&#8217;a pas besoin d&#8217;un champ significatif pour être unique.</li>
<li>Vous pouvez générer l&#8217;ID côté client et l&#8217;envoyer au serveur.</li>
<li>Faire communiquer des systèmes complètement séparés, différents ou par API interposée ne pose aucun problème de référence.</li>
</ul>
<p>Pour toutes ces raisons, les bases de données NoSQL (CouchDB, MongoDB, etc) utilisent depuis longtemps les UUID comme clés primaires par défaut. Le moteur de base de données de Google, Big Table, utilise des UUID.</p>
<p>Pourtant les UUID ne sont pas exempts de défauts:</p>
<ul>
<li>Les JOINS sont beaucoup plus lents.</li>
<li>Il prennent plus d&#8217;espace disque et en mémoire.</li>
<li>On ne peut pas les mettre dans des URL sans que ce soit très très moche.</li>
<li>Ils sont difficiles à retenir, dicter et rechercher manuellement.</li>
<li>Ils sont non significatifs. Regardez un UUID ne vous donne aucune info sur les données sous-jacentes.</li>
<li>Ils ne sont pas ordonnés. Cela a un impact sur la manipulation des données, et sur certains moteurs de BDD à l&#8217;insertion.</li>
</ul>
<p>Les UUID ne sont donc pas la solution miracle à tous les soucis, mais ils sont tout de même mon choix par défaut en ce moment ne serait-ce que pour les fixtures. Je gagne les performances sur le caching et le parallélisme, et <a href="http://www.codeproject.com/Articles/388157/GUIDs-as-fast-primary-keys-under-multiple-database">un peu de lenteur sur les JOINS</a> est quelque chose que je peux supporter. Pour les gros sites, les JOINS sont de tout façon votre ennemi juré et on finit toujours par tweaker à grand coup de dé-normalisation.</p>
<p>On peut faire passer ses modèles Django aux UUID en faisant:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #ff7700;font-weight:bold;">from</span> uuid <span style="color: #ff7700;font-weight:bold;">import</span> uuid4
&nbsp;
<span style="color: #ff7700;font-weight:bold;">class</span> MotDElle<span style="color: black;">&#40;</span><span style="color: #008000;">object</span><span style="color: black;">&#41;</span>:
    ...
    <span style="color: #008000;">id</span> = models.<span style="color: black;">CharField</span><span style="color: black;">&#40;</span>max_length=<span style="color: #ff4500;">36</span>, primary_key=<span style="color: #008000;">True</span>,
                          default=<span style="color: #ff7700;font-weight:bold;">lambda</span>: <span style="color: #008000;">str</span><span style="color: black;">&#40;</span>uuid.<span style="color: black;">uuid4</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>, editable=<span style="color: #008000;">False</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Ou, si vous utilisez <a href="https://github.com/django-extensions/django-extensions">django_extensions</a> (et vous devriez, ne serait-ce que pour <code>shell_plus</code> et <code>runserver_plus</code>):</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #ff7700;font-weight:bold;">from</span> django_extensions.<span style="color: black;">db</span>.<span style="color: black;">fields</span> <span style="color: #ff7700;font-weight:bold;">import</span> UUIDField
&nbsp;
<span style="color: #ff7700;font-weight:bold;">class</span> MotDElle<span style="color: black;">&#40;</span><span style="color: #008000;">object</span><span style="color: black;">&#41;</span>:
    ...
    <span style="color: #008000;">id</span> = UUIDField<span style="color: black;">&#40;</span>primary_key=<span style="color: #008000;">True</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Ce qui a l&#8217;avantage de caster la valeur en un objet UUID, et non une bête string, à la lecture.</p>
<p>Malheureusement, pour le moment il n&#8217;y a aucune implémentation officielle de Django pour utiliser les UUID. Cela a des conséquences fort ennuyeuses:</p>
<ul>
<li>Les implémentations actuelles utilisent un <code>VARCHAR</code> pour stocker l&#8217;UUID au lieu d&#8217;un type natif quand c&#8217;est possible, et donc ce n&#8217;est pas du tout optimisé. L&#8217;exception étant <a href="https://github.com/jpwatts/django-pgfields">django-pdfield</a>, mais dans ce cas, adieu la compatibilité entre plusieurs SGBD.</li>
<li><code>django.contrib.auth.models.User</code> n&#8217;a aucun moyen d&#8217;utiliser proprement les UUID (il ne vous reste que le monkey patching). Cela pourrait changer avec Django 1.5 qui prévoit un modèle <code>User</code> extensible. \o/</li>
</ul>
<p>Un <a href="https://code.djangoproject.com/ticket/4682">ticket</a> pendouille depuis 5 ans sur la question. Je vous invite d&#8217;ailleurs à le spammer jusqu&#8217;à ce que réouverture s&#8217;en suive. Et le premier qui me dit &#8220;t&#8217;as qu&#8217;à l&#8217;implémenter, toi&#8221;, je lui retourne un tampon dans la poire.</p>


feed_id: http://sametmax.com/?p=3127
title: Beau et facile à utiliser: deux choses bien différentes
uri: Beau-et-facile-à-utiliser-deux-choses-bien-différentes
url: http://sametmax.com/beau-et-facile-a-utiliser-deux-choses-bien-differentes/
content:
<p>Je suis ergonome de formation. La première chose que j&#8217;ai apprise, c&#8217;est que mon intuition est à chier. Dit très clairement: si je design un site Web basé sur ce que je pense être utilisable, je vais me planter.</p>
<p>Même après des années d&#8217;expérience, mes premières idées sont très classiques, formatées, et Max me met des taquets derrière la tête régulièrement en guise de rappel.</p>
<p>Pour rendre une interface utilisable, il n&#8217;y a qu&#8217;un moyen fiable: le test. Pour apprendre en une journée tout ce que sais de l&#8217;ergonomie, vous pouvez en fait plus ou moins vous limiter à lire et appliquer le <a href="http://www.eyrolles.com/Informatique/Livre/9782744021893?societe=nodesway">bouquin culte de Steve Krug</a>.</p>
<p>Et c&#8217;est quelque chose que les designers ont du mal à comprendre. Ils font souvent des choses très belles, mais n&#8217;est pas Apple qui veut. Faire quelque chose de beau ET d&#8217;utilisable est très difficile.</p>
<p>Et si on doit choisir, <a href="http://37signals.com/svn/posts/1407-why-the-drudge-report-is-one-of-the-best-designed-sites-on-the-web">il vaut mieux faire utilisable que beau</a>.</p>
<h2>Les états</h2>
<p>Les états sont par exemple un vrai problème. En informatique, il n&#8217;y a pas vraiment de moyen de connaître l&#8217;état de quelque chose, et donc <strong>on crée artificiellement des repères visuels</strong> en espérant que l&#8217;utilisateur comprenne ce que l&#8217;on veut dire.</p>
<p>Seulement beau n&#8217;est pas forcément explicite. Est-ce que quelqu&#8217;un peut me dire ici quel bouton correspond à l&#8217;état &#8220;on&#8221; ?</p>
<div id="attachment_3128" class="wp-caption aligncenter" style="width: 500px"><a href="http://sametmax.com/wp-content/uploads/2012/11/731270.jpg"?9d7bd4"><img class=" wp-image-3128 " title="On / Off, l'état le plus simple du monde" src="http://sametmax.com/wp-content/uploads/2012/11/731270.jpg"?9d7bd4" alt="Bouton on / off" width="490" height="210" /></a><p class="wp-caption-text">On / Off, l&#39;état le plus simple du monde</p></div>
<p>Le premier bouton, il est sur &#8220;off&#8221; parce qu&#8217;il affiche &#8220;off&#8221; ou il est sur &#8220;on&#8221;, offrant la possibilité de slider vers l&#8217;état &#8220;off&#8221; ? Les deux comportements existent dans le monde matériel.</p>
<p>Nous avons déjà des boutons qui reflètent très bien on / off: les checkboxes. Tout le monde sait comment ça marche, mais c&#8217;est moche, alors la plupart des designers essayent de les remplacer.</p>
<p>Si la designite vous démange, il faut alors sérieusement réfléchir, et ne pas proposer une solution moins efficace que ce qui existe déjà. Par exemple, une bonne implémentation du concept ci-dessus est:</p>
<div id="attachment_3129" class="wp-caption aligncenter" style="width: 500px"><a href="http://sametmax.com/wp-content/uploads/2012/11/731711.jpg"?9d7bd4"><img class=" wp-image-3129 " title="Un tout petit détail..." src="http://sametmax.com/wp-content/uploads/2012/11/731711.jpg"?9d7bd4" alt="Slide on / off avec effet lumineux" width="490" height="210" /></a><p class="wp-caption-text">Un tout petit détail...</p></div>
<p>L&#8217;auteur a ici ajouté un simple effet grisé sur le &#8220;off&#8221; (qui a la connotation de &#8220;désactivé&#8221;) et un effet de lumière sur le &#8220;on&#8221; (qui à la connotation de &#8220;en fonctionnement&#8221;). On sait clairement que le premier est l&#8217;état &#8220;off&#8221;, et que si on clique dessus, on va obtenir le second état: &#8220;on&#8221;.</p>
<p>Mais les états ne sont pas toujours aussi simples que on / off, et surtout, ils se cachent parfois dans des situations naturelles. <a href="http://37signals.com/svn/">37signals</a> ont largement défendu l&#8217;idée de parer à ce que l&#8217;utilisateur va vouloir faire, plutôt que d&#8217;attendre qu&#8217;il le fasse. Et cela passe par la prédictibilité, et la compréhension du contexte, donc par l&#8217;<strong>affichage d&#8217;états et d&#8217;intentions</strong>.</p>
<p>Un exemple simple: l&#8217;état vide. Vous n&#8217;imaginez pas combien il est courant de ne pas travailler l&#8217;état de départ, ou vide, d&#8217;une UI. Pourtant, c&#8217;est primordial car c&#8217;est le premier contact de l&#8217;utilisateur avec votre logiciel, et surtout, par principe, vide signifie qu&#8217;il n&#8217;y a aucun indice sur ce qu&#8217;il faut faire par défaut.</p>
<p>Prenez l&#8217;explorateur de fichiers par défaut d&#8217;Ubuntu, Nautilus. Il est globalement très bon. En revanche, sur les gros dossiers, ou sur les dossiers contenant beaucoup de thumbnails, il y a un instant plus ou moins long durant lequel on ne sait pas si il charge, ou si le dossier est vide.</p>
<div id="attachment_3130" class="wp-caption aligncenter" style="width: 504px"><a href="http://sametmax.com/wp-content/uploads/2012/11/Capture-du-2012-11-17-103558.png"?9d7bd4"><img class=" wp-image-3130 " title="Il n'y a rien dans ce dossier" src="http://sametmax.com/wp-content/uploads/2012/11/Capture-du-2012-11-17-103558.png"?9d7bd4" alt="Capture d'écran de Nautilus dans un dossier vide" width="494" height="356" /></a><p class="wp-caption-text">Il n&#39;y a rien dans ce dossier</p></div>
<p>Une fois qu&#8217;on a décidé que l&#8217;état &#8220;n&#8217;affiche rien&#8221; était bien non un temps de chargement, mais le fait qu&#8217;il n&#8217;y a rien à afficher, le cerveau fait la déduction, &#8220;le dossier est vide&#8221;.</p>
<p>Prenez par contre Marlin, l&#8217;explorateur d&#8217;Elementary OS, et donc bien moins intégré à Unity, dans lequel il ressort plus laid que Nautilus. Mais il vous montre instantanément de quoi il est question.</p>
<div id="attachment_3131" class="wp-caption aligncenter" style="width: 527px"><a href="http://sametmax.com/wp-content/uploads/2012/11/Capture-du-2012-11-17-104129.png"?9d7bd4"><img class=" wp-image-3131 " title="Marlin est un projet très prometteur" src="http://sametmax.com/wp-content/uploads/2012/11/Capture-du-2012-11-17-104129.png"?9d7bd4" alt="Capture d'écran de Marlin dans un dossier vide" width="517" height="359" /></a><p class="wp-caption-text">Marlin est un projet très prometteur</p></div>
<p>Ceci vous parait un détail. En fait, certains geeks trouvent même énervant tous ces trucs qui &#8220;ne servent à rien&#8221; pour &#8220;les gens qui ne veulent pas réfléchir&#8221; car &#8220;c&#8217;est quand même pas compliqué de voir que le dossier est vide&#8221;.</p>
<p>Oui, sauf que comme je vous en parlais précédemment, il existe une telle chose que la <a href="http://sametmax.com/bien-expliquer-quelque-chose-les-regles-de-base/">charge cérébrale</a>, et que tout ce qui y participe se cumule.</p>
<p>Faire un beau design allège la charge cérébrale, mais faire un design utilisable la soulage sans commune mesure. Qui dit moins de charge, dit une utilisation fluide, sans peur (car oui, la peur de cliquer est un facteur étonnamment important dans le schéma de décision des utilisateurs lambdas), et donc des users qui aimeront votre app.</p>
<p>Le but est d&#8217;obtenir le même résultat que le crayon: <strong>quand vous écrivez, vous pensez à ce que vous écrivez, pas au crayon</strong>. Bien sûr que réfléchir un tout petit peu n&#8217;est pas la mer à boire, mais c&#8217;est autant de neurones que vous consacrez à votre outil plutôt qu&#8217;à votre travail.</p>
<p>Mais faire un design, plus que beau, utilisable, c&#8217;est aussi proposer à l&#8217;utilisateur ce qu&#8217;il peut faire. Mettre en avant les solutions les plus importantes. Les menus ajoutent à la charge cérébrale, ce sont des accès secondaires.</p>
<p>UsabilityFriction a posté une bonne <a href="http://usabilityfriction.com/2010/11/10/case-study-empty-state/">illustration de la démarche</a>. Ils sont partis d&#8217;un truc vide et pas top:</p>
<div id="attachment_3132" class="wp-caption aligncenter" style="width: 610px"><a href="http://sametmax.com/wp-content/uploads/2012/11/Empty.png"?9d7bd4"><img class=" wp-image-3132 " title="Vous n'avez pas de photo. Merci. Au revoir." src="http://sametmax.com/wp-content/uploads/2012/11/Empty.png"?9d7bd4" alt="Mockup d'un porte folio" width="600" height="360" /></a><p class="wp-caption-text">Vous n&#39;avez pas de photo. Merci. Au revoir.</p></div>
<p>Et ils ont ajouté:</p>
<ul>
<li>Des raccourcis vers les actions de certains menus pour ajouter des photos.</li>
<li>Un album photo d&#8217;exemple facilement supprimable pour que l&#8217;utilisateur puisse déjà se balader.</li>
<li>Une vidéo de démo qui disparait dès qu&#8217;on ajoute un élément.</li>
<li>Une courte et simple explication en forme d&#8217;invitation à l&#8217;action.</li>
</ul>
<div id="attachment_3133" class="wp-caption aligncenter" style="width: 610px"><a href="http://sametmax.com/wp-content/uploads/2012/11/BetterEmpty-Pt2.png"?9d7bd4"><img class=" wp-image-3133 " title="Vous n'avez pas de photos. Mais vous pouvez faire tout ça !" src="http://sametmax.com/wp-content/uploads/2012/11/BetterEmpty-Pt2.png"?9d7bd4" alt="Mockup d'un porte folio amélioré" width="600" height="469" /></a><p class="wp-caption-text">Vous n&#39;avez pas de photos. Mais vous pouvez faire tout ça !</p></div>
<p>Ici il n&#8217;y a pas d&#8217;enjeu esthétique car c&#8217;est un mockup. Et c&#8217;est tout l&#8217;interêt du mockup pourri, fait avec <a href="http://www.balsamiq.com/">balsamiq</a> ou même au feutre Veleda sur brouillon: on se soucie de l&#8217;utilisabilité, pas du look. Le premier est la priorité car un bon designer rendra votre site qui est déjà facile à utiliser beau, alors que rendre un site déjà designé facile à utiliser demande beaucoup plus de travail additionnel.</p>
<h2>Un bon dessin vaut mieux qu&#8217;un long discours, sauf si on dessine mal</h2>
<p>Utiliser des icônes, c&#8217;est bien, non ?</p>
<p>En théorie, les formes et couleurs sont plus faciles et rapides à identifier que des mots. Et on évite les problèmes de traduction.</p>
<p>Mais, le hic, c&#8217;est que la signification d&#8217;une icône, contrairement à un mot, n&#8217;est pas garantie:</p>
<ul>
<li style="text-align: justify;">Il existe des centaines de milliers de mots. On est loin d&#8217;avoir autant d’icônes.</li>
<li style="text-align: justify;">Les concepts abstraits sont très durs à icônifier. Essayez de trouver un symbole pour &#8220;niveau de difficulté&#8221; pour voir&#8230;</li>
<li style="text-align: justify;">Selon le contexte (culturel, expérience, environnement&#8230;), un symbole peut avoir des sens différents. Ainsi, le blanc est la couleur du mariage pour nous, mais du deuil dans certains pays musulmans. Le <a href="http://www.ergonomie-interface.com/methodes-process-techniques/internationalisation-site-internet/">rouge</a> est la couleur du mariage en Chine&#8230;</li>
<li style="text-align: justify;">Les icônes se périment plus vite que les mots. On a en encore beaucoup de logiciels qui symbolisent &#8220;sauvegarder&#8221; par une icône en forme de disquette. Combien d&#8217;utilisateurs actuels savent à quoi sert une disquette ? Ou même ce que c&#8217;est ?</li>
</ul>
<p>Et si on choisit les icônes, on est obligé d&#8217;en mettre de manière cohérente, donc quand on rajoute un nouveau bouton, c&#8217;est une nouvelle icône à rajouter: il faut en trouver une correspondante, et au sens, et au design.</p>
<p>Un exemple: j&#8217;aime le nouveau design de Gmail. Mais le tout icône n&#8217;est pas forcément une réussite. Dans l&#8217;ancienne version, trouver comment marquer un mail en tant que spam était évident:</p>
<div id="attachment_3134" class="wp-caption aligncenter" style="width: 583px"><a href="http://sametmax.com/wp-content/uploads/2012/11/spam_text.jpg"?9d7bd4"><img class=" wp-image-3134 " title="Le mot spam est très facile à reconnaître: court et à faible ambiguïté" src="http://sametmax.com/wp-content/uploads/2012/11/spam_text.jpg"?9d7bd4" alt="Capture d'écran de l'ancien menu mail de Gmail" width="573" height="54" /></a><p class="wp-caption-text">Le mot spam est très facile à reconnaître: court et à faible ambiguïté</p></div>
<p>Le nouveau design est plus beau, mais par contre, pour mettre son mail en spam&#8230;</p>
<div id="attachment_3135" class="wp-caption aligncenter" style="width: 492px"><a href="http://sametmax.com/wp-content/uploads/2012/11/spam_icon.jpg"?9d7bd4"><img class=" wp-image-3135 " title="Difficile de faire le lien entre un hexagone avec un point d'exclamation et &quot;spam&quot;" src="http://sametmax.com/wp-content/uploads/2012/11/spam_icon.jpg"?9d7bd4" alt="Capture d'écran du nouveau menu mail de Gmail" width="482" height="59" /></a><p class="wp-caption-text">Difficile de faire le lien entre un hexagone avec un point d&#39;exclamation et &quot;spam&quot;</p></div>
<p>L&#8217;objectif n&#8217;est pas de pinailler sur les qualités de x ou z, mais d&#8217;illustrer. <a href="http://stackoverflow.com/">Stackoverflow</a> est un modèle d&#8217;utilisabilité, mais le site comporte pourtant très peu d&#8217;icônes. <a href="http://mnmlist.com/">Mnmlist</a> prouve qu&#8217;on peut être jusqu&#8217;au boutiste pour aller à l&#8217;essentiel. Drudge report prouve que&#8230; heu&#8230; <a href="http://37signals.com/svn/posts/1407-why-the-drudge-report-is-one-of-the-best-designed-sites-on-the-web">Je vous laisse lire</a>.</p>
<p>Encore une fois, ne laissez pas la fièvre graphique prendre la priorité sur l&#8217;utilisabilité. <strong>Un beau design est important. Un design utilisable est primordial</strong>. Il n&#8217;existe pas de solution clé en main telle que &#8220;utilisons des icônes&#8221; qui pallie le travail de réflexion ergonomique dont votre projet à besoin.</p>
<p>Tous les types de designs ont leur place: avec et sans icônes, avec des images, sans, avec du texte, sans, avec des jeux de couleur, sans. La recette à elle seule ne peut pas rendre un plat délicieux, il faut de bons cuisiniers, de bons ingrédients et du travail.</p>
<p>(et la métaphore de la bouffe est particulièrement adaptée, car quel que soit l&#8217;acharnement que vous mettez à votre popotte, y aura toujours un connard pour trouver ça dégueulasse)</p>
<p>Un dernier exemple de &#8220;ça dépend&#8221;. Gedit (Gnome) VS Scratch (Elementary OS), deux éditeurs de texte, deux approches pour &#8220;l&#8217;état de départ&#8221;, aucune n&#8217;est meilleure que l&#8217;autre, et elles ne satisferont pas le même public.</p>
<div id="attachment_3136" class="wp-caption aligncenter" style="width: 557px"><a href="http://sametmax.com/wp-content/uploads/2012/11/Capture-du-2012-11-17-105342.png"?9d7bd4"><img class=" wp-image-3136 " title="Je préfère l'approche de Gedit: on commence cash à éditer, c'est plus efficace" src="http://sametmax.com/wp-content/uploads/2012/11/Capture-du-2012-11-17-105342.png"?9d7bd4" alt="Capture d'écran de Gedit sur un fichier vide" width="547" height="457" /></a><p class="wp-caption-text">Je préfère l&#39;approche de Gedit: on commence cash à éditer, c&#39;est plus efficace</p></div>
<p>&nbsp;</p>
<div id="attachment_3137" class="wp-caption aligncenter" style="width: 510px"><a href="http://sametmax.com/wp-content/uploads/2012/11/Screen-Shot-2011-10-31-at-10.33.11-500x347.png"?9d7bd4"><img class="size-full wp-image-3137" title="Un non dev sera parfois plus à l'aise avec une indication claire de ce qui va se passer" src="http://sametmax.com/wp-content/uploads/2012/11/Screen-Shot-2011-10-31-at-10.33.11-500x347.png"?9d7bd4" alt="Capture d'écran de Scratch sur un fichier vide" width="500" height="347" /></a><p class="wp-caption-text">Un non dev sera parfois plus à l&#39;aise avec une indication claire de ce qui va se passer</p></div>
<p>Tout comme on oriente son design en fonction de son public (<a href="http://news.ycombinator.com/">hacker news</a> peut se permettre l&#8217;aspect WEB 1.0, pas Facebook), l&#8217;ergonomie doit viser aussi le type d&#8217;utilisateur auquel vous souhaitez plaire. Car il n&#8217;y a aucune chance que vous plaisiez à tout le monde.</p>


feed_id: http://sametmax.com/?p=3501
title: Il n’y a aucune loi qui interdise de nettoyer un tunnel
uri: Il-n-y-a-aucune-loi-qui-interdise-de-nettoyer-un-tunnel
url: http://sametmax.com/il-ny-a-aucune-loi-qui-interdise-de-nettoyer-un-tunnel/
content:
<p>Parfois votre client va vous demander un truc tordu, ou vous poser des contraintes à la con. Parfois votre  cousin relou vient passer le WE la même date que votre plan cul. Parfois on donne une formation Python sous Windows&#8230;</p>
<p>Quand ça m&#8217;arrive, j&#8217;essaye de me souvenir de l&#8217;exemple d&#8217;Alexandre Orion, un artiste Brésilien qui a été plusieurs fois interpellé brutalement par la police pour avoir décoré, petit à petit, les murs d&#8217;un tunnel à fort passage avec un <a href="http://www.wired.com/underwire/2007/10/dirty-trick-cau/">énorme ossuaire</a>.</p>
<p>Sa protestation contre la pollution ne l&#8217;a néanmoins jamais mené en prison, car il connaissait les règles. Il a juste un peu triché.</p>
<p>Au lieu de tagger des os sur les murs, il a choisi les endroits les plus sales, et a nettoyé la surface jusqu&#8217;à laisser apparaître la couleur blanche sous-jacente, dessinant par extrusion des cranes bien visibles.</p>
<p><strong>La police l&#8217;a chopé plusieurs fois, mais il n&#8217;a jamais eu de problème avec la justice, car il n&#8217;y a pas de loi qui interdise de nettoyer un tunnel.</strong></p>
<p>La prochaine fois que votre client vous demande un thème rose fluo, que votre meuf vous invite au dîner dominicale avec belle-maman, que votre pote super adroit vient vous emprunter votre bagnole, rappelez-vous qu&#8217;il y peut-être quelque chose à jouer avec la contrainte.</p>
<p>Tout comme il n&#8217;y a aucun courage à ne pas avoir peur, car le courage c&#8217;est de se bouger le cul malgré la trouille, on est pas créatif si on à les mains complètement libres. Ne vous plaignez pas que la situation n&#8217;es pas idéale, changez juste légèrement plan.</p>


feed_id: http://sametmax.com/?p=3575
title: (Très) Grand listing des libs standards les plus utiles en Python
uri: (Très)-Grand-listing-des-libs-standards-les-plus-utiles-en-Python
url: http://sametmax.com/tres-grand-listing-des-libs-standard-partie-les-plus-utiles-en-python/
content:
<p class="title">Dans la lignée du <a href="http://sametmax.com/tres-grand-listing-des-libs-tierce-partie-les-plus-utiles-en-python/">(Très) Grand listing des libs tierce partie les plus utiles en Python</a>, voici la même chose mais pour les libs qui sont fournies en standard avec Python.</p>
<p class="title">Bien entendu, il y a déjà une liste (bien plus complète), <a href="http://docs.python.org/2.7/library/index.html">dans la documentation officielle</a>. Mais la version ci-dessous vous propose uniquement les modules les plus utiles, en français, et surtout, avec une description de ce que vous pouvez faire avec (plutôt qu&#8217;une définition abstraite). Bonne découverte !</p>
<p>&nbsp;</p>
<table border="0" cellspacing="0">
<colgroup width="250"></colgroup>
<colgroup width="161"></colgroup>
<colgroup width="323"></colgroup>
<tbody>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE" height="16"><strong>Sujet</strong></td>
<td style="border: 1px solid #000000;" align="CENTER"><strong>Nom de la bibliothèque</strong></td>
<td style="border: 1px solid #000000;" align="CENTER"><strong>Description</strong></td>
</tr>
<tr>
<td style="border: 1px solid #000000;" colspan="3" align="CENTER" valign="MIDDLE" bgcolor="#EEEEEE" height="18">Texte</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="6" align="CENTER" valign="MIDDLE" height="226">Extraction et formatage</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/string.html">string</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Plein de choses dépréciées, mais une liste de constantes intéressantes comme par exemple tous les caractères ASCII en minuscule.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/re.html">re</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Rechercher, extraire, splitter et remplacer avec des expressions rationnelles</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/difflib.html">difflib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Analyser la différence entre deux textes</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/logging.html">logging</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Puissant module pour créer des logs. Pratique pour stocker discrètement les erreurs, ou enregistrer l&#8217;activité de votre service dans un fichier.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/fnmatch.html">fnmatch</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Vérifie si une chaîne correspond à une motif de recherche unix. Par exemple « *.py » va matcher script.py. Une alternative simple aux expressions rationnelles pour créer des filtres.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/shlex.html">shlex</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer un petit parseur pour syntaxe régulière. On peut créer des mini-langages avec ou parser un fichier avec un format étrange.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="4" align="CENTER" valign="MIDDLE" height="117">Encodage</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/codecs.html">codecs</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Opérations en vrac autour des encodages : lister les codecs disponibles, ouvrir un fichier dans un encodage précis, etc</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/unicodedata.html">unicodedata</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Principalement utile pour convertir les caractères spéciaux en leur équivalent ASCII. Ex : é =&gt; e</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/base64.html">base64</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Encode vers et décode base16, 32 et 64.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/binascii.html">binascii</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Conversion du binaire vers l&#8217;ASCII et inversement.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="3" align="CENTER" valign="MIDDLE" height="99">Contrôle</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/getpass.html">getpass</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Demander à l&#8217;utilisateur son mot de passe en ligne de commande, de manière sécurisée.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/hashlib.html">hashlib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Sommes de contrôle en md5, sha1, sha224, sha256, sha384, sha512</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/hmac.html">hmac</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Vérifier authentification d&#8217;un message signé crytographiquement</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="2" align="CENTER" valign="MIDDLE" height="113">Localisation</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/gettext.html">gettext</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Boîte à outil pour fournir votre programme dans plusieurs langues. Ça ne vous dispense pas de traduire, mais ça remplace la traduction par la bonne version pour vous.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/locale.html">locale</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Quelques facilités pour adapter votre programme selon l&#8217;origine de votre utilisateur (détection de la région, formatage des chiffres, etc).</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" colspan="3" align="CENTER" valign="MIDDLE" bgcolor="#EEEEEE" height="18">Types avancés</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="3" align="CENTER" valign="MIDDLE" height="130">Manipulation du temps</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/datetime.html">datetime</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Gestion des dates et des durées incluant la comparaison, l&#8217;addition, le formatage et le parsing.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/time.html">time</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Informations sur l&#8217;horaire : fuseaux, heure d&#8217;hivers, etc.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/calendar.html">calendar</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Permet de répondre à des question existentielles telle que : « 1996 était-elle une année bissextile ? » ou « combien y a-t-il de jour dans le mois suivant si j&#8217;avance de 67 jours ?»</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="2" align="CENTER" valign="MIDDLE" height="113">Références</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/weakref.html">weakref</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer une référence faible vers un objet de tel sorte que sa copie n&#8217;empêche pas le passage du garbage collector.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/copy.html">copy</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Mécanismes de copie superficielle et de copie complète des objets. L&#8217;assignation ne retournant qu&#8217;une référence, c&#8217;est utile si on veut une vrai copie.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="3" align="CENTER" valign="MIDDLE" height="146">Performance</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/ctypes.html">ctypes</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Appeler des fonctions C depuis Python. On peut même charger des .dll et des .so.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/heapq.html">heapq</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Transforme une liste en un arbre binaire et permet de bénéficier de fort gain de performances sur certains algos de tris.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/array.html">array</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer des tableaux typés (contrairement aux listes qui peuvent contenir des objets de plusieurs types). Beaucoup plus rapide à manipuler qu&#8217;une liste.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="3" align="CENTER" valign="MIDDLE" height="146">Collections</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/collections.html">collections</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Si les listes, tuples, dictionnaires et sets ne suffisent pas, ce module contient des tuples nommés, des dictionnaires ordonnés, des deques et des compteurs optimisés.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/queue.html">Queue</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Une file synchronisée utilisable pour partager des ressources qui vont être accédées de manière concurrente (ex : avec plusieurs threads).</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/pprint.html">pprint</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Affiche joliment les listes, les dictionnaires, etc. Très pratique pour débugger.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" colspan="3" align="CENTER" valign="MIDDLE" bgcolor="#EEEEEE" height="18">Maths</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="4" align="CENTER" valign="MIDDLE" height="148">Calcul</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/math.html">math</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Regroupe les fonctions mathématiques les plus courantes : puissance, exponentiel, log, etc.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/cmath.html">cmath</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Comme le module math, mais pour les nombres complexes.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/decimal.html">decimal</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Un type spécial qui permet de manipuler des chiffres à virgule sans le problème habituel de l’arrondi en informatique.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/fractions.html">fractions</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Un type spécial qui permet de manipuler des fractions, et non leur résultat.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="2" align="CENTER" valign="MIDDLE" height="82">Génération pseudo aléatoire</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/random.html">random</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Retourne des nombres « au hasard » selon des bornes ou des répartitions spécifiques.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/uuid.html">uuid</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Génère un identifiant garanti d&#8217;être unique à travers le monde. Il y a 2 puissance 128 combinaison possibles.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" colspan="3" align="CENTER" valign="MIDDLE" bgcolor="#EEEEEE" height="18">Outils de développement</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="3" align="CENTER" valign="MIDDLE" height="192">Concurrence</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/threading.html">threading</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Exécuter du code dans un thread séparé. Permet de ne pas bloquer si fait beaucoup d&#8217;I/O (téléchargement, lecture de fichiers, etc). Mais pas de gain sur la vitesse de calcul si on a un processeur à plusieurs cœurs.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/multiprocessing.html">multiprocessing</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Exécuter du code dans un processus séparé. Mêmes bénéfices que les threads, en moins léger, mais avec un gain de vitesse sur les calculs si on a un processeur à plusieurs cœur.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/signal.html">signal</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Envoyer des signaux à son propre programme. Par exemple, interrompre une opération si elle prend trop de temps.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="3" align="CENTER" valign="MIDDLE" height="53">Debugging</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/pdb.html">pdb</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Debuggueur intégré à Python</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/timeit.html">timeit</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Calculer le temps que met un code à s’exécuter</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/trace.html">trace</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Suivre ce que fait un programme, pas à pas</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="7" align="CENTER" valign="MIDDLE" height="300">Boîte à outils</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/itertools.html">itertools</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Toute sorte de manipulation sur les itérables : chaîner, lire en boucle, dupliquer, lire un morceau sous condition, etc</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/functools.html">functools</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Outils pour faciliter la programmation fonctionelles : fonctions partielles, copie de metadata d&#8217;une fonction vers une autre, etc</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/operator.html">operator</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Tous les opérateurs (+, %, &amp;, [], &gt;&gt;, …) sous forme de fonction.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/argparse.html">argparse</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Automatise le parsing des arguments passés à votre script. Génère « &#8211;help » automatiquement. Gère les sous-commandes et les vérifications essentielles.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/atexit.html">atexit</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Demander à Python d’exécuter une fonction quand il s&#8217;arrête.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/contextlib.html">contextlib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Outils pour créer des context managers (ce qui s&#8217;utilise avec le mot clé « with »). Permet notamment de créer facilement un context manager à partir d&#8217;un simple générateur.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/sched.html">sched</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Files d&#8217;attentes dans laquelle on met à la queue des fonctions à exécuter plus tard.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="4" align="CENTER" valign="MIDDLE" height="148">Code</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/pydoc.html">pydoc</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Générer automatiquement la documentation depuis votre code</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/doctest.html">doctest</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lancer des tests unitaires à partir des exemples écrits dans les docstrings de votre programme.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/unittest.html">unittest</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Le standard pour les tests unitaires en Python</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/2to3.html">2to3</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Automatise la conversion d&#8217;un code Python 2 en un code Python 3. Ne fait pas tout le travail, mais fait gagner beaucoup de temps. Un outil inverse existe : 3to2.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="7" align="CENTER" valign="MIDDLE" height="433">Introspection</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/inspect.html">inspect</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Permet d&#8217;obtenir toutes les meta informations possibles à propos de toutes les objets du programme. Contient notamment des fonctions pour savoir si un objet est un générateur, un module, ou une classe.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/abc.html">abc</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Une implémentation des classes abstraites en Python. Pas vraiment indispensable, mais si vous rencontrez du code qui l&#8217;utilise, vous saurez à quoi ça sert.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/gc.html">gc</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Manipuler le garbage collector. Par exemple vous pouvez le désactiver.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/warnings.html">warnings</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Module principalement importé par les gens qui en ont marre de voir leur console pleine de DeprecationWarning.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/traceback.html">traceback</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">A garder sous le coude pour le jour où vous aurez à attraper une erreur, et afficher d&#8217;où elle viens dans le code dans votre propre format.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/__future__.html">__future__</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Facilite la transition vers les version suivantes de Python en autorisant l&#8217;import de fonctionnalités optionnelles qui deviendront obligatoires plus tard. Ainsi, from __future__ import print_function permet d&#8217;utiliser la fonction print() de Python 3 en Python 2.7.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/__builtin__.html">__builtin__</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Contient toutes les fonctions built-in de Python : open, str, list, all, etc. Peut utile, sauf pour se rafraîchir la mémoire ou créer un système d&#8217;autocomplétion.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" colspan="3" align="CENTER" valign="MIDDLE" bgcolor="#EEEEEE" height="18">Fichiers et dossiers</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="8" align="CENTER" valign="MIDDLE" height="342">Système de fichiers</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/os.path.html">os</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Très gros module qui va de la manipulation de chemin et nom de fichiers à la vérification de permissions.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/stat.html">stat</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Contient des fonctions pour analyser les appels de os.stats. Surtout utile pour gagner en performance et éviter de multiples appels si on est intéressé par plusieurs types d&#8217;informations sur un fichier. Sinon, utiliser plutôt les fonctions de os autre que os.stat.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/mimetypes.html">mimetypes</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Deviner le type d&#8217;un fichier selon son mimetype déclaré.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/shutil.html">shutil</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Opération en masse sur les fichiers comme supprimer récursivement une arborescence</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/mailcap.html">mailcap</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Définir qu&#8217;il faut ouvrir un programme pour gérer une fichier de tel mimetype est fait à travers à mailcap, que ce module permet de manipuler.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/glob.html">glob</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lister les fichiers d&#8217;un répertoire en utilisant la syntaxe de filtre d&#8217;Unix. Ex : « *.py » va lister tous les fichiers Python.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/filecmp.html">filecmp</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Compare des arborescences et permet de traiter leurs différences.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/tempfile.html">tempfile</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer des dossier et des fichiers temporaires.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="3" align="CENTER" valign="MIDDLE" height="161">Contenu de fichiers</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/linecache.html">linecache</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Récupérer un ligne n&#8217;importe où dans un fichier, efficacement.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/io.html">io</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Fournit des objets buffers. Entre autre utile pour cumuler des chaînes de caractères ou manipuler un objet avec l&#8217;interface d&#8217;un fichier en mémoire vive.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/mmap.html">mmap</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Manipuler un fichier réel comme si il était en mémoire vive, à travers l&#8217;interface habituelle des fichiers, ou comme une chaîne de caractères mutable.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="3" align="CENTER" valign="MIDDLE" height="158">Persistance</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/pickle.html">pickle</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Sérialiser n&#8217;importe quelle structure de données Python. Permet de transformer en texte des objets de toute sorte, et inversement. La version en C du module(<a href="http://docs.python.org/2.7/library/pickle.html#module-cPickle">cPickle</a>), parfois disponible, est plus rapide.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/shelve.html">shelve</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Un dictionnaire, mais qu&#8217;on peut sauvegarder sur le disque, et recharger plus tard.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/sqlite3.html">sqlite3</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer, lire et écrire dans une base de données SQLite, qui est une base de données complète, ACID, supportant presque tout SQL92.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" colspan="3" align="CENTER" valign="MIDDLE" bgcolor="#EEEEEE" height="18">Système</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="5" align="CENTER" valign="MIDDLE" height="147">Interfaces utilisateur</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/curses.html">curses</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer des interfaces en ligne de commande</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/readline.html">readline</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Implémenter un historique ou de l&#8217;autocompletion pour une UI en ligne de commande.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/cmd.html">cmd</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Facilite la création d&#8217;un shell avec des mots clés en guise de commande</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/webbrowser.html">webbrowser</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Ouvre le navigateur Web par défaut à l&#8217;adresse donnée.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/tkinter.html">Tkinter</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Interface graphique par défaut fournie avec Python. Assez pauvre et mal intégrée à l&#8217;OS.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="3" align="CENTER" valign="MIDDLE" height="130">Installation</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/sys.html">sys</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Informations sur le votre environnement : variable d&#8217;environnement, paramètres du script, limite de récursion, chemin d&#8217;import, etc</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/platform.html">platform</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Tout ce que Python sait sur la machine qu&#8217;il l&#8217;héberge : OS, version, processeur, etc.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/sysconfig.html">sysconfig</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Nombreuses informations sur l&#8217;installation de Python : flag de compilation, version, dossiers d&#8217;installation, etc.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="2" align="CENTER" valign="MIDDLE" height="66">Processus</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/errno.html">errno</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Code d&#8217;erreurs utilisés par Python lorsqu&#8217;un processus échoue. Utile pour dissocier plusieurs types d&#8217;IOError.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/subprocess.html">subprocess</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Exécuter une programme externe.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" colspan="3" align="CENTER" valign="MIDDLE" bgcolor="#EEEEEE" height="18">Formats</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="5" align="CENTER" valign="MIDDLE" height="88">Compression</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/zlib.html">zlib</a></td>
<td align="LEFT">Lire et écrire le format bzip</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/gzip.html">gzip</a></td>
<td align="LEFT">Lire et écrire le format gzip</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/bz2.html">bz2</a></td>
<td align="LEFT">Lire et écrire le format bzip2</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/zipfile.html">zipfile</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lire et écrire des fichiers zip</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/tarfile.html">tarfile</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lire et écrire des fichiers tar</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="4" align="CENTER" valign="MIDDLE" height="225">Langages de balise</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/sgmllib.html">sgmllib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Parser du SGML. Le format est surtout utilisé par l&#8217;industrie du livre, donc vous le rencontrerez peu.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/htmllib.html">htmllib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Parser du HTML. Il est presque toujours mieux d&#8217;utiliser une bibliothèque tierce partie pour cela.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/htmllib.html#module-htmlentitydefs">htmlentitydefs</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Une liste de entités HTML pour ISO Latin-1 et des fonctions pour convertir dans un sens et dans l&#8217;autre. Résout parfois des problèmes d&#8217;encodage épineux.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/xml.etree.elementtree.html">xml.etree.ElementTree</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Manipulation d&#8217;un fichier XML : analyse, création, export, etc. Sax (lecture rapide) et Dom (création via l&#8217;API standard) sont disponibles mais je recommande plutôt ElementTree pour la lecture (ou lxml si vous pouvez l&#8217;installer) et un langage de template pour la production.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="5" align="CENTER" valign="MIDDLE" height="175">Autres formats</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/csv.html">csv</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lire et produire des fichiers CSV. DictReader est particulièrement utile, car il prend en compte les en-tête. Suffisant pour 80 % des cas où l&#8217;utilisateur veut un fichier compatible Excel.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/configparser.html">ConfigParser</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lire et écrire les fichiers INI. Principalement utilisé pour la configuration.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/robotparser.html">robotparser</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lire les fichiers robot.txt.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/json.html">json</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Transforme du JSON en type natif Python, et inversement.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/plistlib.html">plistlib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lire les fichiers de configurations binaires de Mac OS.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" colspan="3" align="CENTER" valign="MIDDLE" bgcolor="#EEEEEE" height="18">Réseau</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" colspan="3" align="CENTER" valign="MIDDLE" bgcolor="#FFFFFF" height="33"><em>J&#8217;évite ici volontairement les très nombreux module qui ont pour but de vous permettre d&#8217;implémenter votre propre serveur pour le protocole X ou Z. Si vous lisez cet article, vous n&#8217;en avez probablement pas besoin.</em></td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="4" align="CENTER" valign="MIDDLE" height="194">Communication entre machines</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/socket.html">socket</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Module de manipulation bas niveau des sockets en Python. À moins de savoir exactement ce que vous faite, je vous conseille plutôt d&#8217;utiliser PyZmq ou Twisted.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/asyncore.html">asyncore</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Boîte à outil fournissant des outils basiques pour la programmation asynchrone en Python. Même remarque que précédement.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/asynchat.html">asynchat</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Exemple d&#8217;implémentation d&#8217;une communication client / serveur avec asyncore. Même remarque que précédemment</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/ssl.html">ssl</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Permet de se connecter à un serveur de manière sécurisée en utilisant le chiffrement SSL.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="5" align="CENTER" valign="MIDDLE" height="228">Email</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/email.html">email</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Parser et créer des emails. L&#8217;email est un format complexe. Ne faites pas ça à la main. Utiliser ce module.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/mailbox.html">mailbox</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lire et écrire dans différent format de mail box, c&#8217;est à dire les formats de stockage des emails par les clients mails tels que mbox.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/poplib.html">poplib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Se connecter et interagir avec un serveur POP pour lire les mails</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/imaplib.html">imaplib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Se connecter et interagir avec un serveur IMAP pour lire les mails</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/smtplib.html">smtplib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Se connecter et interagir avec un serveur SMTP pour envoyer des mails. Notez qu&#8217;il faut plus qu&#8217;un code qui marche pour envoyer des mails du fait des nombreux garde-fous pour limiter le spam.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="6" align="CENTER" valign="MIDDLE" height="307">Web</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/urlparse.html">urlparse</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Extraire les différentes parties d&#8217;une URL</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/simplehttpserver.html">SimpleHTTPServer</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lancer un petit serveur HTTP. Très pratique pour les tests ou pour partager un fichier sur son réseau local. Ne pas utiliser ça en production.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/cookie.html">Cookie</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Lire et écrire dans le format propre aux cookies.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/cookielib.html">cookielib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Gestion automatique des cookies. A utiliser en conjonction avec urllib et urllib2 pour simuler un utilisateur réel. Vu la complexité de l&#8217;interface, installez plutôt mechanize et requests si vous le pouvez.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/urllib.html">urllib</a> Et <a href="http://docs.python.org/2.7/library/urllib2.html">urllib2</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Permet de faire des requêtes sur une URL donnée et lire la réponse. Les deux modules se recoupent largement, mais certaines fonctionalités sont disponibles dans l&#8217;un ou l&#8217;autre. Même remarque concernant la complexité que pour le module précédent.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/httplib.html">httplib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Bibliothèque de bas niveau pour travailler avec HTTP, et utilisée par urllib. Rarement utile, sauf parfois pour importer une exception.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" rowspan="4" align="CENTER" valign="MIDDLE" height="148">Autres protocoles</td>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/ftplib.html">ftplib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer un client FTP pour envoyer et recevoir des fichiers</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/nntplib.html">nntplib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer un client NNTP pour lire des news sur Usenet</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/telnetlib.html">telnetlib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer un client telnet. Utile pour controler du vieux matiriel à distance, comme certains routeurs.</td>
</tr>
<tr>
<td style="border: 1px solid #000000;" align="CENTER" valign="MIDDLE"><a href="http://docs.python.org/2.7/library/xmlrpclib.html">xmlrpclib</a></td>
<td style="border: 1px solid #000000;" align="LEFT" valign="MIDDLE">Créer un client XMLRCP pour appeler des méthodes d&#8217;un objet dans un autre programme. Surtout utilisé dans le monde Java.</td>
</tr>
</tbody>
</table>


feed_id: http://sametmax.com/?p=3572
title: Lancer une fonction automatiquement à l’arrêt de Python
uri: Lancer-une-fonction-automatiquement-à-l-arrêt-de-Python
url: http://sametmax.com/lancer-une-fonction-automatiquement-a-larret-de-python/
content:
<p>Vous avez des envies de sortie grandiloquentes ? Ou juste besoin d&#8217;un peu de ménage à l&#8217;arrêt de la machine virtuelle de Python ?</p>
<p><a href="http://docs.python.org/2.7/library/atexit.html">Il y a un module pour ça</a>™.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">atexit</span>
&nbsp;
<span style="color: #808080; font-style: italic;"># la version courte</span>
@<span style="color: #dc143c;">atexit</span>.<span style="color: black;">register</span>
<span style="color: #ff7700;font-weight:bold;">def</span> strange_game<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>:
    <span style="color: #ff7700;font-weight:bold;">print</span> <span style="color: #483d8b;">&quot;What about a nice game of chess ?&quot;</span>
&nbsp;
&nbsp;
<span style="color: #ff7700;font-weight:bold;">def</span> last_word<span style="color: black;">&#40;</span>word=<span style="color: #483d8b;">&quot;rosebud&quot;</span><span style="color: black;">&#41;</span>:
    <span style="color: #ff7700;font-weight:bold;">print</span> word
&nbsp;
<span style="color: #808080; font-style: italic;"># la version qui autorise des arguments</span>
<span style="color: #dc143c;">atexit</span>.<span style="color: black;">register</span><span style="color: black;">&#40;</span>last_word, word=<span style="color: #483d8b;">&quot;Monde de merde&quot;</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Les fonctions ne sont pas garanties d&#8217;être appelées dans un ordre précis.</p>


feed_id: http://sametmax.com/?p=3591
title: Vous en pensez quoi de cette idée ?
uri: Vous-en-pensez-quoi-de-cette-idée
url: http://sametmax.com/vous-en-pensez-quoi-de-cette-idee/
content:
<p>Bon, peut être qu&#8217;il y 3 idées en fait. Ou plus, tout dépend.</p>
<pre>[23:03:11] sam: tu sais, je me dis qu'un truc qui manque
[23:03:19] sam: c'est la possibilité de générer des données aléatoirement
[23:03:22] sam: gerne
[23:03:42] sam: D(l=100, S(), I())
[23:03:48] sam: ça créer un dico de 100 item
[23:04:00] sam: avec un string aléatoire en entrée
[23:04:26] sam: et un entier aléatoire en value
[23:04:34] sam: entée => clé pardon
[23:04:40] sam: ça serait pratique pour les tests
[23:04:52] sam: et c'est relou à créer à la main dans un shell
pour tester des trucs
[23:05:10] sam: Meux
[23:05:19] sam: D(S(), L())[:100]
[23:06:05] sam: Et si tu veux des trucs vraiment préci
[23:06:36] sam: L(T(Prenom(source=('british', 'fantasy')))[3:5])[500:1500]
[23:07:27] sam: Une liste entre 500 et 1500 élément de tuples entre 3
et 5 élément qui sont des prénoms d'origine britanique ou d'heroic fantasy
[23:08:55] sam: (matte arte)
[23:09:16] sam: y a pas de smiley matte arté
[23:09:24] max: regarde Arte
[23:09:41] max: bon et alors ton truc tu veux en faire quoi ? une lib ?
[23:09:43] sam: je lance
[23:09:46] sam: oui une lib
[23:10:15] max: bah j'en sais rien moi j'en vois pas l'utilité mais
parceque j'y ai ptet jamais pensé ou eu besoin
[23:11:07] max: d'ailleurs ça commence à me saouler toutes ces libs :)
[23:11:12] sam: lol
[23:11:15] sam: t'as raison
[23:11:22] max: avant hier j'ai voulu réinstall un serveur d'encoding
[23:11:22] sam: je pense que tu devrais tout coder à la main
[23:11:25] max: j'ai passé la journée
[23:11:35] max: bon ct pas vraiment les libs mais encore ce ffmpeg
[23:11:38] sam: ahahahaha
[23:11:43] sam: recode ffmpeg alors !
[23:11:49] max: d'où l'idée que je t'avais dis de faire un site
de build avec options
23:12:27] … heureusement pour les libs j'avais le requierements
tu me diras mais bon ça empeche pas qu'il faut des fois installer
 des trucs derriere comme mysql-python, python-devel, etc
[23:13:12] max: c pratique je dis pas
[23:13:17] sam: ^^
[23:13:24] max: mais en plus j'ai tendance à en utiliser pas mal
pour pas grand chose
[23:13:25] sam: je suis pas raciste
[23:13:28] sam: mais il faut avouer que les noirs
[23:13:35] max: du coup faut pas oublier les requietements
[23:14:02] max: sont jeunes là
[23:14:52] sam: cette concersation merite un article
[23:15:08] max: :p
[23:15:40] max: tiens idée
[23:15:48] max: pas torp conne mais qui rapporte rien
[23:16:14] max: faire un script qui scanne ton projet et te
 génére un fichier requierements que si les libs sont utilisées
[23:16:32] sam: hum, pas con du tout
[23:16:34] max: avec eventuellement des comments dans le
requieremnt avec le fichier + ligne où est appelée la lib
[23:16:39] max: genre à la rosetta
[23:16:53] max: comme ça tu peux cleaner tes pips de temps en temps
sans tout péter
[23:17:01] max: sans compter les patchs
[23:19:03] max: tu regarde les monthy là ? sont bons ces cons :)
[23:19:08] sam: j'aime pas en français
[23:19:52] max: etonnant pour arte d'hab ils mette vost
[23:20:31] sam: je matte misfit du coup
[23:21:22] sam: là y a un héros qui s'est fait volé sa bite
[23:21:38] sam: et deux autres qui mattent des femmes
enceintes en train de faire du stretching
[23:21:46] sam: j'adore cette série
</pre>


feed_id: http://sametmax.com/?p=3603
title: la technologie qui nous entoure, toujours plus présente et toujours plus compliquée
uri: la-technologie-qui-nous-entoure-toujours-plus-présente-et-toujours-p
url:
http://sametmax.com/la-technologie-qui-nous-entoure-toujours-plus-presente-et-toujours-plus-compliquee/

content:
<p>Les appareils qui nous entourent nous envahissent de plus en plus et sont de plus en plus compliqués. Une simple radio devient de suite un satellite de la NASA pour celui qui n&#8217;aura pas la maitrise de l&#8217;informatique.</p>
<p><strong>Bouhhh encore un naze qui est contre l&#8217;évolution ! Espèce de vieux fossile&#8230;</strong></p>
<p>J&#8217;ai arrêté de regarder la télé il y a environ 14 ans, quand je dis arrêter c&#8217;est les programmes TV, j&#8217;ai une télé et je regarde encore des bons vieux films et quelques uns plus récents qui sont bien imaginés.<br />
Quand je zappe pour essayer de trouver un bon nanard ou un &#8220;Vintage&#8221; avec Stallone ou schwarzi je tombe sur des pubs et je trouve que ces dernières années la réclame pour les technos a littéralement explosée, je dirais depuis l&#8217;iPhone à peu près.</p>
<p>Je suis sidéré par le nombre d&#8217;options qu&#8217;on essait de nous faire gobber en 30 secondes, les appareils photos et leurs 300 000 gigapixels seconde, les Ipad mini super maxi pour votre mouflet à 600 euros pièce, les imprimantes termo-laser à double injection bi-turbo, les voitures <a href="http://www.youtube.com/watch?v=rmEkGKyKwmQ">citronopipo</a> et j&#8217;en passe et des meilleures.</p>
<p>Passé un âge on &#8220;imprime&#8221; plus tout cette info parcequ&#8217;on s&#8217;en fout d&#8217;abord et puis parcequ&#8217;on comprend pas (l&#8217;un allant surement avec l&#8217;autre). J&#8217;imagine bien que les publicitaires sont pas fous et que si ils bombardent la télé de cette façon c&#8217;est qu&#8217;il doit y avoir des vaches à traire à l&#8217;autre bout&#8230;Quoique&#8230;</p>
<p>Ouais j&#8217;avoue je connais pas toutes les options de mon appareil photo giga cool, de ma télé ultra HD surround 2Khz, de mon grille-pain Sony, de mon chiotte Panasonic et j&#8217;assume.<br />
Mais il y a pire, la génération avant nous !</p>
<p><strong>La ménagère de 50 ans en a rien à foutre !</strong><br />
Je vais pas avoir besoin de mendater un audit auprès de la population, pas plus tard que ce week-end j&#8217;ai eu une discussion passionante avec ma mère sur un cadre photo numérique que je lui ai offert il y a 2 ans et qu&#8217;elle a retrouvée dans&#8230;un tirroir.</p>
<p><strong>Quelques points frappants:</strong></p>
<p style="padding-left: 30px;"><strong>Il faut mettre quoi comme piles ?</strong><br />
Qu&#8217;est-ce qui marche encore avec des piles à part le vibro de ma soeur et encore ? Plus grand chose, la majorité des appareils électroniques sont sous batteries, et pour beaucoup il faut un cordon &#8230;USB</p>
<p style="padding-left: 30px;"><strong>C&#8217;est quoi USB ?</strong><br />
Demandez à vos parents, même aux trentenaires qui sont pas dans l&#8217;info? vous allez rire. Le plus marrant c&#8217;est que pour ces appareils bien souvent il n&#8217;y a que l&#8217;USB pour les charger donc il faut&#8230; un ordi allumé pour les recharger !! (il y a des adaptateurs 220V/USB mais qui en a ? Je veux dire, vraiment&#8230;Qui en a ?)</p>
<p style="padding-left: 30px;"><strong>La mémoire dans la peau !</strong><br />
Encore un pur moment. Ma mère n&#8217;a absolument pas la notion de carte mémoire, et oui elle est de la génération des cassettes VHS, des disques vinyles, du gramopho&#8230; Alors allez lui epxliquer qu&#8217;une petite carte de 2cm de large contient toutes ses photos de ses enfants chéris, qu&#8217;elle peut écrire et effacer autant de fois qu&#8217;elle veut, mais au fait ces photos elles sont en quel format ? quelle résolution ?<br />
J&#8217;ai tenté de lui expliquer qu&#8217;elle pouvait les transferer de l&#8217;appareil photo vers l&#8217;ordi pour les traiter et ensuite les mettre sur le cadre, ou simplement retirer la carte mémoire de l&#8217;appareil photo pour la mettre directement dans le cadre. Je vous laisse imaginer sa tête :)</p>
<p style="padding-left: 30px;"><strong>Si je le débranche il s&#8217;etteind ?</strong><br />
La peur, l&#8217;angoisse, le trac, si je débranche ça s&#8217;etteind ? alors je perds toutes mes photos ?! Bon je touche pas,  je laisse comme ça&#8230;. Et un ordi allumé avec son cadre photo qui pendouille,  enchainé par son câble USB. Je suis sur que vous êtes en train de rire là comme j&#8217;ai pu rire sur le moment&#8230;</p>
<p style="padding-left: 30px;"><strong>Ha oui c&#8217;est jolie mais ça tourne pas les photos, c&#8217;est cassé ?</strong><br />
Téléfunken et le cadre photo, du grand art, pas d&#8217;indication de l&#8217;état de la batterie, 3 boutons sur le haut et essayez de comprendre comment on met en mode diaporama&#8230; Il a bien un menu à l&#8217;ecran avec écrit <em>Random</em> mais ma mère ne lit pas l&#8217;anglais, mon père s&#8217;en fout, c&#8217;est balot madame chombier !</p>
<p>Bon je me suis bien marré. Il n&#8217;empêche que sur le chemin du retour j&#8217;ai commencé à me poser des questions, là c&#8217;était juste un cadre photo, quizz du dernier Smartphone Chipokomon, des appareils photos numériques, des télés pleines d&#8217;options&#8230;<a href="http://www.nikopik.com/2012/12/les-tv-connectees-de-samsung-vulnerables-aux-attaques-a-distance.html">Et de virus.</a><br />
Mon père se debrouille un peu mieux (non je ne dis pas que c&#8217;est parceque c&#8217;est un homme&#8230;) mais il a toujours une question à me poser sur comment on fait ci ou on fait ça. Et ça prend du temps, et ça m&#8217;emmerde&#8230;</p>
<p>Bientôt on ne va plus faire un pas sans avoir de l&#8217;electronique compliquée sous la main à configurer, maintenir, faire réparer, etc..<br />
J&#8217;aime le progrès, j&#8217;aime la technologie. Mais je me demande si le tournant que ça prend n&#8217;est pas un peu too much.<br />
Barder d&#8217;options des appareils électroniques les rendants compliqués à utiliser et vite obsolètes est-il vraiment le bon moyen de faire évoluer notre environnement technologique ? Celà ne va-til pas finir par nous dégouter de tout ces &#8220;gadgets&#8221; ?</p>
<p>J&#8217;espère que nous sommes juste à une époque charnière et que les appareils du futurs seront plus intuitifs et plus simples à utiliser, que la course aux options laissera la place à une totale liberté de pensée cosmique vers un nouvel age réminiscent&#8230; Amen</p>


feed_id: http://sametmax.com/?p=3653
title: Bon, c’est officiel, le bouton “soucrire à nos conneries” est pêté
uri: Bon-c-est-officiel-le-bouton-soucrire-à-nos-conneries-est-p
url: http://sametmax.com/bon-cest-officiel-le-bouton-soucrire-a-nos-conneries-est-pete/
content:
<p>Suite au rapport d&#8217;un gentil lecteur, on s&#8217;est apperçu que ça marchait pas. Donc si vous recevez rien, c&#8217;est pas de votre faute, c&#8217;est de la nôtre.</p>
<p>On a mis nos meilleurs limiers sur le coup. </p>
<p>Nan en fait pour l&#8217;instant on joue surtout avec l&#8217;idée de virer la feature parceque débugguer WordPress nous enchante moyen moins.</p>


feed_id: http://sametmax.com/?p=3604
title: La subtance chimique qui créé des serial killers a-t-elle été découverte ?
uri: La-subtance-chimique-qui-créé-des-serial-killers-a-t-elle-été-déc
url: http://sametmax.com/la-subtance-chimique-qui-cree-des-serial-killers-a-t-elle-ete-decouverte/
content:
<p>Notre société va de plus en plus mal, c&#8217;est un fait. Avec l&#8217;immigration en pleine explosion et la baisse du pouvoir d&#8217;achat provoquée par l&#8217;arrivée de l&#8217;euro, la criminalité a augmenté. Au point qu&#8217;aujourd&#8217;hui on entend de plus en plus parler de <a href="http://tempsreel.nouvelobs.com/societe/20111122.FAP8194/rapport-sur-la-criminalite-augmentation-des-meurtres-entre-conjoints.html">meurtres violents</a> au journal de 20h. </p>
<p>Bien entendu, la consommation massive des jeux vidéos est sans aucun doute un <a href="http://odieuxconnard.wordpress.com/2012/12/09/le-jeu-video-voila-lennemi/">facteur important</a> de cette tendance, mais <strong>une découverte récente tend à faire penser qu&#8217;une <a href="http://www.abc.net.au/science/articles/2006/05/17/1631494.htm?site=science/greatmomentsinscience">substance chimique</a> pourrait également avoir provoqué ces gestes malheureux</strong>.</p>
<h2>Ce produit, c&#8217;est le monoxyde de dihydrogène</h2>
<p>Utilisé massivement dans les centrales nucléaires comme agent décalorifiant et en grande quantité par les plus gros noms de la pétro-chimie, notamment comme solvant, il est pourtant <strong>légal et facile de s&#8217;en procurer en France</strong> pour tout particulier.</p>
<p>Du fait de son <strong>faible coût </strong>et de présence à de nombreux échelons de production, on en retrouve maintenant dans de nombreux produits cosmétiques et même dans des produits alimentaires de grande consommation.</p>
<p>Maintenant la pire nouvelle, la voici: <strong>durant les deux dernières années, tous les acteurs des crimes les plus violents , incluant <a href="http://www.lefigaro.fr/international/2012/11/26/01003-20121126ARTFIG00564-une-video-choc-d-anders-breivik-publiee.php">Breivik</a>, et <a href="http://tempsreel.nouvelobs.com/tag/mohamed-merah">Merah</a>, avait dans leur corps des taux énormes de monoxyde de dihydrogène</strong>. Un examen de leurs routines régulières montre qu&#8217;ils étaient régulièrement exposés à des doses massives du produit. Plus fort encore, le jour de la catastrophe, ils avaient tous, sans exception, été contaminés lors d&#8217;une absorption par voie orale.</p>
<p>À noter que la subtance elle-même est loin d&#8217;être anodine pour l&#8217;homme:</p>
<ul>
<li><strong>son inhalation, même en faible quantité, peut causer une mort par asphyxie</strong>;</li>
<li>sa forme gazeuse peut causer de graves brûlures;</li>
<li>le contact prolongé avec sa forme solide provoque des lésions des tissus;</li>
<li>en contact avec le mauvais agent patogène, elle est propice au développement de maladies telles que le choléra.</li>
</ul>
<p>Pour ces raisons, elle est depuis longtemps utilisée dans des cas de torture ou lors d&#8217;interventions policières contre des manifestants. Et oui, même dans des démocraties !</p>
<p>Les impacts environnementaux sont eux aussi potentiellement élevés:</p>
<ul>
<li>elle est un élément principal des pluies acides;</li>
<li>elle contribue à l’érosion des sols;</li>
<li>sa forme poudreuse, en particulier concentrée en plaques instables, peut être un obstacle au développement harmonieux des loisirs de montagne.</li>
</ul>
<h2>
Il est urgent que le public soit mis au courant</h2>
<p>De notre côté, nous allons un peu plus creuser deux autres produits qui nous semblent littéralement ignorés par les autorités sanitaires et judiciaires:</p>
<p>- l&#8217;<a href="http://www.eurekalert.org/pub_releases/2012-11/wtsi-bds111212.php">acide désoxyribonucléique</a>, mesurable en quantité alarmante dans la viande de supermarché et que l&#8217;on retrouve à des taux énormes lors de toutes les autopsies des 10 dernières années; Il serait un facteur clé dans l&#8217;apparition des maladies génétiques.<br />
- l&#8217;<a href="http://ja.wikipedia.org/wiki/%E3%82%A2%E3%82%BB%E3%83%81%E3%83%AB%E3%82%B5%E3%83%AA%E3%83%81%E3%83%AB%E9%85%B8">acide acétylsalicylique</a>, un médicament utilisé par ses propriétés antiagrégantes plaquettaires, mais disponible sans ordonnance, et souvent consommé par les grands buveurs d&#8217;alcool. Il y aurait aussi un lien avec les patients atteind de fièvres.</p>


feed_id: http://sametmax.com/?p=3659
title: L’un de vous a un cadeau de Noël qui l’attend au pied du sapin…
uri: L-un-de-vous-a-un-cadeau-de-Noël-qui-l-attend-au-pied-du-sapin
url: http://sametmax.com/lun-de-vous-a-un-cadeau-de-noel-qui-lattend-au-pied-du-sapin/
content:
<div id="attachment_3662" class="wp-caption aligncenter" style="width: 394px"><img class=" wp-image-3662 " title="mere-noel-sexy (1)" src="http://sametmax.com/wp-content/uploads/2012/12/mere-noel-sexy-1.jpg"?9d7bd4" alt="" width="384" height="191" /><p class="wp-caption-text">J&#39;ai un cadeau en-dessous...</p></div>
<p>On &#8216;a pas beaucoup d&#8217;argent, on n&#8217;a pas d&#8217;ami, on n&#8217;a pas de chien, on n&#8217;a pas de bagnole mais on a un peu de coeur.Le ptit Sam et moi-même avons reçu la visite de la mère Noëlle l&#8217;autre soir vers 10 heures du matin. Et entre deux Ricards elle nous a gentillement pom&#8230; proposée de venir livrer un cadeau de Noël à un de nos lecteurs chéri.</p>
<p>On n&#8217;a pas fait d&#8217;annonce avant du genre &#8220;inscrivez-vous&#8221;, &#8220;jeu sans obligation d&#8217;achat&#8221;, etc car chez les Rougemonts on ne parle pas, on agit ! Donc juste un ptit article vite fait.</p>
<p>Et puis pour que cet article soit constructif Sam vous propose un petit code en Python de tirage au sort. Le script va prendre au hasard un pseudo parmis le top 20 des commentateurs.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #ff7700;font-weight:bold;">import</span> argparse
<span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">random</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">import</span> MySQLdb
&nbsp;
<span style="color: #dc143c;">parser</span> = argparse.<span style="color: black;">ArgumentParser</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
&nbsp;
<span style="color: #dc143c;">parser</span>.<span style="color: black;">add_argument</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'database'</span>, <span style="color: #008000;">type</span>=<span style="color: #008000;">str</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">parser</span>.<span style="color: black;">add_argument</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'--host'</span>, <span style="color: #008000;">type</span>=<span style="color: #008000;">str</span>, default=<span style="color: #483d8b;">&quot;localhost&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">parser</span>.<span style="color: black;">add_argument</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'--port'</span>, <span style="color: #008000;">type</span>=<span style="color: #008000;">int</span>, default=<span style="color: #ff4500;">3306</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">parser</span>.<span style="color: black;">add_argument</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'--user'</span>, <span style="color: #008000;">type</span>=<span style="color: #008000;">str</span>, default=<span style="color: #483d8b;">&quot;&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">parser</span>.<span style="color: black;">add_argument</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'--passwd'</span>, <span style="color: #008000;">type</span>=<span style="color: #008000;">str</span>, default=<span style="color: #483d8b;">&quot;&quot;</span><span style="color: black;">&#41;</span>
&nbsp;
args = <span style="color: #dc143c;">parser</span>.<span style="color: black;">parse_args</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
&nbsp;
db = MySQLdb.<span style="color: black;">connect</span><span style="color: black;">&#40;</span>host=args.<span style="color: black;">host</span>, port=args.<span style="color: black;">port</span>, <span style="color: #dc143c;">user</span>=args.<span style="color: #dc143c;">user</span>,
                     passwd=args.<span style="color: black;">passwd</span>, db=args.<span style="color: black;">database</span><span style="color: black;">&#41;</span>
&nbsp;
cursor = db.<span style="color: black;">cursor</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
&nbsp;
results = cursor.<span style="color: black;">execute</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;&quot;&quot;
    SELECT comment_author, comment_author_email, count(*) as total
    FROM wp_comments
    WHERE comment_author NOT IN ('sam', 'max')
    GROUP BY comment_author
    ORDER BY total DESC
    LIMIT 22
&quot;&quot;&quot;</span><span style="color: black;">&#41;</span>
&nbsp;
users = <span style="color: #008000;">list</span><span style="color: black;">&#40;</span>cursor<span style="color: black;">&#41;</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">print</span> <span style="color: #483d8b;">&quot;Choosing among:&quot;</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">for</span> <span style="color: #dc143c;">user</span> <span style="color: #ff7700;font-weight:bold;">in</span> users:
    <span style="color: #ff7700;font-weight:bold;">print</span> <span style="color: #483d8b;">&quot;<span style="color: #000099; font-weight: bold;">\t</span>- %s&quot;</span> <span style="color: #66cc66;">%</span> <span style="color: #dc143c;">user</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span><span style="color: black;">&#93;</span>.<span style="color: black;">decode</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'latin-1'</span><span style="color: black;">&#41;</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">print</span> <span style="color: #483d8b;">&quot;<span style="color: #000099; font-weight: bold;">\n</span>And the winner is...<span style="color: #000099; font-weight: bold;">\n</span>&quot;</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">print</span> u<span style="color: #483d8b;">&quot;%s (%s)<span style="color: #000099; font-weight: bold;">\n</span>&quot;</span> <span style="color: #66cc66;">%</span> <span style="color: #008000;">tuple</span><span style="color: black;">&#40;</span>s.<span style="color: black;">decode</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'latin-1'</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">for</span> s <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #dc143c;">random</span>.<span style="color: black;">choice</span><span style="color: black;">&#40;</span>users<span style="color: black;">&#41;</span><span style="color: black;">&#91;</span>:<span style="color: #ff4500;">2</span><span style="color: black;">&#93;</span><span style="color: black;">&#41;</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">print</span> <span style="color: #483d8b;">&quot;Ta da!&quot;</span></pre></div></div>


<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">&nbsp;
$ python tirage.py sametmax <span style="color: #660033;">--user</span> sametmax <span style="color: #660033;">--passwd</span> voussaurezpas<span style="color: #000000; font-weight: bold;">@!</span>
Choosing among:
    - roro
    - foxmask
    - Recher
    - etienne
    - Muchos
    - Baronsed
    - JeromeJ
    - Luigi
    - JEEK
    - desfrenes
    - Freak0
    - fero14041
    - Kontre
    - François
    - anthony
    - LowsLiago
    - H3
    - Soli
    - kinezana
    - chassegnouf
    - Xavier Combelle
    - pfroot
&nbsp;
And the winner is...
&nbsp;
foxmask <span style="color: #7a0874; font-weight: bold;">&#40;</span>xxxx<span style="color: #000000; font-weight: bold;">@</span>xxxxxxx<span style="color: #7a0874; font-weight: bold;">&#41;</span>
&nbsp;
Ta da<span style="color: #000000; font-weight: bold;">!</span></pre></div></div>

<p>D&#8217;après le script c&#8217;est <strong>foxmask</strong> qui a gagné(e), merci de nous <a href="http://sametmax.com/contactez-nous/">envoyer ton adresse postale</a> pour recevoir au plus vite ton cadeau.<br />
Ce n&#8217;est pas une blague, on a vraiment un cadeau pour toi (et c&#8217;est PAS de la merde!) ;)</p>
<p>Merci de nous lire et passez tous de bonnes fêtes, mettez-vous en plein la panse!</p>
<p>PS: Pour les autres ben&#8230;Vous l&#8217;avez dans le cul ! Au prochain tirage au sort :)</p>


feed_id: http://sametmax.com/?p=3689
title: Convertir du binaire en ASCII et vice versa en Python
uri: Convertir-du-binaire-en-ASCII-et-vice-versa-en-Python
url: http://sametmax.com/convertir-du-binaire-en-ascii-et-vice-versa-en-python/
content:
<p>Exercice le plus inutile du monde, puisque les <a href="http://www.roubaixinteractive.com/PlayGround/Binary_Conversion/Binary_To_Text.asp">usages actuels</a> réels sont des plus limités. Tout au plus cela vous permettra de lire la colonne de droite de <a href="http://www.paulds.fr/2010/06/petit-retour-sur-ipfuck/">paulds</a>.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">binascii</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> bin<span style="color: black;">&#40;</span><span style="color: #008000;">int</span><span style="color: black;">&#40;</span><span style="color: #dc143c;">binascii</span>.<span style="color: black;">hexlify</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'Sam &amp; Max'</span><span style="color: black;">&#41;</span>, <span style="color: #ff4500;">16</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">2</span>:<span style="color: black;">&#93;</span>
<span style="color: #483d8b;">'10100110110000101101101001000000010011000100000010011010110000101111000'</span></pre></div></div>

<p>Et l&#8217;inverse:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">binascii</span>.<span style="color: black;">unhexlify</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'%x'</span> <span style="color: #66cc66;">%</span> <span style="color: #008000;">int</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'0b'</span> + <span style="color: #483d8b;">'10100110110000101101101001000000010011000100000010011010110000101111000'</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>
<span style="color: #483d8b;">'Sam &amp; Max'</span></pre></div></div>

<p>Voilà, Voilà.</p>
<p>Non, ça ne sert à rien non. </p>
<p>Bon, sinon pour faire du remplissage : en écrivant cet article, j&#8217;ai remarqué que tout le formatting du code se faisait avec des balises <code>&lt;pre&gt;</code> qui rendait tout plus beau, et je me suis dit &#8220;le bonheur est dans les &lt;pre&gt;.</p>
<p>Ouai j&#8217;avais pas d&#8217;inspiration ce matin.</p>


feed_id: http://sametmax.com/?p=1621
title: Mettre la capote sans casser l’ambiance
uri: Mettre-la-capote-sans-casser-l-ambiance
url: http://sametmax.com/mettre-la-capotte-sans-casser-lambiance/
content:
<p>Preuve que mine de rien la prévention (et la répression :-p) et la communication ça marche pas trop mal, les gens fument moins, mettent la ceinture de sécurité et de plus en plus souvent la <a href="http://www.dailymotion.com/video/x2hneo_les-inconnus-les-preservatifs_shortfilms">capota</a>.</p>
<p>Mais bon, c&#8217;est toujours relou et peut casser le rythme, alors voici quelques astuces pour mettre un préservatif sans transformer l&#8217;étreinte en astreinte.</p>
<h2>Mets la moi !</h2>
<p>Non ce n&#8217;est pas elle qui va dire ça, mais vous.</p>
<p>Après avoir joué un peu, tendez-lui le préservatif en lui demandant de vous la mettre. Un petit sourire en coin en prime ne peut pas faire de mal.</p>
<p>Avantages :</p>
<ul>
<li>On est toujours dans le jeu à deux, plutôt que de faire une transition de quelques secondes où vous êtes tout seul comme un con.</li>
<li>Vous vous faites tripoter, ça garde l&#8217;érection en pleine forme.</li>
<li>Pas mal de filles ne l&#8217;ont jamais fait (!) du coup c&#8217;est parfois très marrant.</li>
<li>Si elle est expérimentée, il y a des variantes (masturbation, à la bouche, à l&#8217;enfilade, etc) qui peuvent carrément rendre ça sympa.</li>
</ul>
<p>Désavantages :</p>
<ul>
<li>Si votre partenaire est inexpérimentée ou manque d&#8217;assurance, elle va flipper car elle ne saura pas comment faire (et certaines ont peur de vous faire mal :-p). Là vous avez intérêt à le voir très vite et à savoir quoi dire sinon le blanc qui va en découler sera plus important que celui que vous vouliez éviter au premier abord.</li>
<li>Si elle a les ongles longs, il y a risque d&#8217;abîmer la capote, et ça ne se verra pas forcément.</li>
<li>Certaines filles font ça mal, et ça fait&#8230; mal. Mais bon, dites vous que c&#8217;est pour toutes les fois où vous vous êtes débrouillé comme un manche en lui démontant un têton ou le clito. Ca arrive un mauvais dosage !</li>
</ul>
<h2>Surprise !</h2>
<p>Enfilez là avant de commencer. Ceci ne marche bien entendu que si vous savez précisément que vous allez vous envoyer en l&#8217;air, et que vous avez un moment discretos une ou deux minutes avant l&#8217;action. Pas évident donc.</p>
<p>Avantages :</p>
<ul>
<li>Zéro temps mort. C&#8217;est comme si vous n&#8217;en aviez pas mis, et c&#8217;est super agréable. La meuf vous posera peut être même la question : &#8220;tu as mis&#8230; ?&#8221;</li>
<li>Pas d&#8217;empressement : ça sera mis et bien mis. Pas de réserve décentrées, d&#8217;élastique  à mi-chemin ou de gland trop serré.</li>
</ul>
<p>Désavantages :</p>
<ul>
<li>Si vous ratez votre timing, votre capote restera trop longtemps dans le froc : assèchement, accumulation de particule, risque de micro-félure. La galère. Et si vous devez la retirer pour en ajouter une autre, ben, pouet.</li>
<li>Si la meuf (pardon, je suis politiquement incorrecte, la personne, car ça pourrait être un autre mec ou une shemale) vous voit avec, elle peut se demander &#8220;mais qui est ce psychopathe qui se balade avec sa queue dans du plastique&#8221; ou autres pensées en votre défaveur.</li>
</ul>
<h2>Chat(te)-bite</h2>
<p>Un bon cuni calé dans les préliminaires, et pendant ce temps on s&#8217;habille le zguege. Largement ma technique préférée, mais demande pas mal de pratique.</p>
<p>Avantages :</p>
<ul>
<li>Tout le monde s&#8217;amuse !</li>
<li>La transition vers la pénétration est super top.</li>
<li>Généralement, effet de surprise la première fois. Très bien vu par la gent féminine en général.</li>
</ul>
<p>Désavantages :</p>
<ul>
<li>Pendant que vous avez votre langue entre ses cuisses et vos mains sur votre bite, vous ne pouvez pas mettre de doigt, pas caresser les seins ou l&#8217;intérieur de ses jambes, pas appuyer sur son bas-ventre ou la maintenir fermement. La léchouille, c&#8217;est qu&#8217;une partie du cuni, donc il faut faire vite.</li>
<li>Parfois on débande en route. Tous les minous ne sont pas excitant à brouter, ou parfois on est juste pas dans le mood et mine de rien, ça dure.</li>
<li>La chatte est à quelques centimètres au dessus du matelas, et vos mains sont occupées. Donc ce sont vos abdos qui font le travail. Quand il faut accélérer, c&#8217;est crevant.</li>
</ul>
<h2>Par derrière</h2>
<p>Un bon massage du dos est une excellente introduction à la levrette, et vous avez tout le temps pour pour enfiler le k-way au cyclope.</p>
<p>Avantages :</p>
<ul>
<li>Pas stressant.</li>
<li>Appelle à une position des plus agréables pour la suite.</li>
</ul>
<p>Désavantages :</p>
<ul>
<li>Faire gaffe à l&#8217;huile de massage utilisée. La plupart abîment les préservatifs.</li>
<li>Le dos se masse à deux mains, donc il faut stratégiquement passer en massage nuque et savoir enfiler le préservatif à une main. Ici, la pratique aide pas mal.</li>
<li>Faut savoir masser. Ben oui, si vous massez comme une buse la séance va vite se finir.</li>
</ul>
<h2>A la bourrine</h2>
<p>Vous comptez sur l&#8217;excitation du moment, vous la jouez naturel, et vous faites ça bien ouvertement, vite fait. C&#8217;est ce que la plupart des gens font.</p>
<p>Avantages :</p>
<ul>
<li>Vous avez rien besoin de prévoir ou de penser. Vu que le sexe est meilleur quand il est instinctif, c&#8217;est un avantage énorme.</li>
<li>Ca ne fait pas &#8220;celui qui a préparé son coup&#8221;. Certaines personnes se diront que vous avez de l&#8217;expérience à avoir choisit une technique avancée, d&#8217;autres penseront que vous êtes un taré. Eh oui, il n&#8217;y a rien qui plaise à tout le monde !</li>
</ul>
<p>Désavantages :</p>
<ul>
<li>Si vous êtes pas fluides, ça peut bien miner l&#8217;ambiance. Enfiler un bout de plastique sur sa verge n&#8217;est PAS un geste sensuel.</li>
<li>La bizarrarie du moment (surtout avec une personne qu&#8217;on connaît encore peu) peut amener au fou-rire. C&#8217;est pas grâve, c&#8217;est bon de se marrer un coup. Pas forcément à mettre dans les désavantages si vous êtes à l&#8217;aise avec l&#8217;idée. Mais parfois on a plus envie de &#8220;ahhhhhhhhhhh ahhhhh&#8221; que de &#8220;ah ah ah&#8221;.</li>
</ul>
<p>Sinon, pour les fêtes le <a href="http://www.leroidelacapote.com/">roi de la capote</a> fait des promos mais il n&#8217;a plus son fameux modèle Kartouche. Snif.</p>


feed_id: http://sametmax.com/?p=3643
title: Personnalisez le démarrage d’iPython
uri: Personnalisez-le-démarrage-d-iPython
url: http://sametmax.com/personnalisez-le-demarrage-dipython/
content:
<p><a href="http://ipython.org/">iPython</a>, c&#8217;est bon. Et ça peut être encore meilleur.</p>
<p>Avant on ajoutait un peu de sel à notre super shell en éditant les fichiers <em>.ipython/ipythonrc</em> et <em>.ipython/ipy_user_conf.py</em>. Mais ça c&#8217;était avant.</p>
<p>Maintenant on fait :</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">$ ipython profile create</pre></div></div>

<p>Ce qui va créer un fichier <code>~/.config/ipython/profile_default/ipython_config.py</code> (et <code>ipython_qtconsole_config.py</code> si vous avez installé la version qt).</p>
<p>Il ne vous reste plus qu&#8217;à éditer ce fichier pour personnaliser le démarrage de iPython.</p>
<h2>Executer du code au démarrage</h2>
<p>N&#8217;importe quelle ligne de code Python ou de commande magique (les trucs qui commencent pas &#8216;%&#8217; qui ne fonctionnent que dans iPython) !</p>
<p>Très utile pour les imports par exemple. Voici ce que je fais moi au démarrage :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">c.<span style="color: black;">TerminalIPythonApp</span>.<span style="color: black;">exec_lines</span> = <span style="color: black;">&#91;</span>
<span style="color: #483d8b;">'%doctest_mode'</span>,
<span style="color: #483d8b;">'import os, sys, re, json'</span>,
<span style="color: #483d8b;">'from datetime import datetime, timedelta'</span>,
<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'
try:
    from path import path
except ImportError:
    pass
'</span><span style="color: #483d8b;">''</span>,
<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'
try:
    import requests
except ImportError:
    pass
'</span><span style="color: #483d8b;">''</span>,
<span style="color: #483d8b;">''</span><span style="color: #483d8b;">'
try:
    from batbelt.structs import *
    from batbelt.objects import attr
    from batbelt.strings import slugify, normalize, json_dumps, json_loads
except ImportError:
    pass
'</span><span style="color: #483d8b;">''</span>
<span style="color: black;">&#93;</span></pre></div></div>

<p>Du coup j&#8217;ai quasiment jamais besoin d&#8217;importer un truc, car ce que j&#8217;utilise le plus est déjà là. <code>%doctest_mode</code> me permet de coller des docstrings sans me fouler.</p>
<h2>Programmation graphique</h2>
<p>iPython possède une boucle principale. Les toolkits graphiques aussi. Si vous faites vos essais du code du second dans le premier, ça va bloquer. Heureusement on peut demander à iPython d&#8217;intégrer la main loop d&#8217;un des toolkits graphiques les plus célèbres en choisissant parmi : &#8216;qt&#8217;, &#8216;wx&#8217;, &#8216;gtk&#8217;, &#8216;glut&#8217;, &#8216;pyglet&#8217; et &#8216;osx&#8217; et en settant :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">c.<span style="color: black;">TerminalIPythonApp</span>.<span style="color: black;">gui</span> = <span style="color: #483d8b;">'qt'</span></pre></div></div>

<h2>Virer le header</h2>
<p>Quand on lance le shell, il vous raconte sa vie. Pour lui dire de fermer sa gueule :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">c.<span style="color: black;">TerminalIPythonApp</span>.<span style="color: black;">display_banner</span> = <span style="color: #008000;">False</span></pre></div></div>

<h2>Lancer un script complet</h2>
<p>Bon, ça c&#8217;est si vous avez de gros besoins&#8230;</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">c.<span style="color: black;">TerminalIPythonApp</span>.<span style="color: black;">file_to_run</span> = <span style="color: #483d8b;">'/path/to/script.py'</span></pre></div></div>

<h2>Sauter la confirmation à la fermeture</h2>
<p>Oui, je suis sûr te vouloir te fermer connard ! Tu crois que j&#8217;ai appuyé sur Ctrl + d par erreur en éternuant ?</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">c.<span style="color: black;">TerminalInteractiveShell</span>.<span style="color: black;">confirm_exit</span> = <span style="color: #008000;">False</span></pre></div></div>

<h2>Choisir son éditeur externe</h2>
<p>Si vous tapez <code>%edit</code> dans iPython, il ouvre un éditeur. Vous tapez votre code, vous sauvegardez, vous fermez. Et iPython récupère le code et l&#8217;éxécute. Par défault il utilise VI. On peut faire mieux.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">c.<span style="color: black;">TerminalInteractiveShell</span>.<span style="color: black;">editor</span> = <span style="color: #483d8b;">'/chemin/vers/sublime-text -w'</span></pre></div></div>


feed_id: http://sametmax.com/?p=3709
title: Le bonheur des frameworks
uri: Le-bonheur-des-frameworks
url: http://sametmax.com/le-bonheur-des-frameworks/
content:
<p style="text-align: center;"><em>Traduction un peu adaptée de l&#8217;article <a href="http://discuss.joelonsoftware.com/default.asp?joel.3.219431">Why I hate framework</a> de Joel Spolsky</em></p>
<p style="text-align: left;">J&#8217;ai voulu construire une petite étagère pour y ranger les condiments.</p>
<p>Ayant fait un peu de menuiserie avant, j&#8217;avais une bonne idée de ce dont j&#8217;avais besoin : un peu de bois et quelques outils de base. Un mètre, une scie, un niveau et un marteau.</p>
<p>D&#8217;ailleurs, si je voulais construire toute une maison, j&#8217;en aurais besoin également. Du coup je suis allé dans une quincaillerie, et j&#8217;ai demandé au vendeur où je pouvais trouver un marteau.</p>
<p>&#8220;- Un marteau ?&#8221;, me répondit-il. &#8220;Plus personne n&#8217;achète des marteaux de nos jours vous savez. Ils sont un peu vieux jeu.&#8221;</p>
<p>Surpris, je lui demande pourquoi.</p>
<p>- &#8220;Et bien, le problème avec les marteaux, c&#8217;est qu&#8217;il y en a plein de différents types. Des marteaux arrache-clou, des masses, des marteaux de tapissier&#8230; Que se passerait-il si vous achetiez un type de marteau et réalisiez que vous avez besoin d&#8217;un autre type plus tard ? Vous devriez achetez un autre marteau pour votre prochaine tâche. Il se trouve que la plupart des gens veulent vraiment un seul marteau qui peut être utilisé pour la majorité des tâches qu&#8217;ils peuvent rencontrer dans leur vie.&#8221;</p>
<p>- &#8220;Ça me parait logique. Pouvez-vous me dire où je peux trouver un marteau universel ?&#8221;</p>
<p>- &#8220;Non, nous ne les vendons plus. Ils sont obsolètes.&#8221;</p>
<p>- &#8220;Vraiment ? Je pensais que vous veniez de dire que le marteau universel était l&#8217;avenir.&#8221;</p>
<p>- &#8220;Il se trouve que, si vous faites un seul marteau qui puisse être utilisé pour toutes sortes de tâches, il n&#8217;est vraiment bon, à aucune d&#8217;entre elles. Enfoncer un clou avec une masse n&#8217;est pas très efficace. Et pour tuer votre petite amie, rien ne vaut un marteau de tapissier.&#8221;</p>
<p>- &#8220;C&#8217;est clair ! Donc, si plus personne n&#8217;achète des marteaux universels, et que vous ne vendez plus de marteaux à l&#8217;ancienne, quels marteaux vendez-vous ?&#8221;</p>
<p>- &#8220;En fait, nous n&#8217;en vendons pas.&#8221;</p>
<p>- &#8220;Alors&#8230;&#8221;</p>
<p>- &#8220;D&#8217;après nos recherches, ce dont les gens ont besoin n&#8217;est pas un marteau universel du tout. Il vaut toujours mieux avoir le bon marteau pour le bon boulot. Donc, nous avons commencé à vendre des fabriques de marteau, capable de produire n&#8217;importe quel marteau qui pourrait vous intéresser. Tout ce dont vous avez besoin est de remplir la fabrique de travailleurs, lancer la machinerie, acheter les matériaux de base, payer les charges et hop, vous avez *exactement* le type de marteau dont vous avez besoin en un clin d’œil.&#8221;</p>
<p>- &#8220;Mais je ne veux pas acheter une fabrique de marteaux&#8230;&#8221;</p>
<p>- &#8220;Parfait. Car nous n&#8217;en vendons plus.&#8221;</p>
<p>- &#8220;Attendez, vous venez de me dire que&#8230;&#8221;</p>
<p>- &#8220;Nous avons découvert que la plupart des gens n&#8217;ont pas besoin d&#8217;une fabrique complète de marteaux. Certains, par exemple, n&#8217;auront jamais besoin d&#8217;un marteau de tapissier. (Peut être qu&#8217;ils n&#8217;ont pas d&#8217;ex. Ou peut être qu&#8217;ils les ont tué avec des pics à glace.). Donc il n&#8217;y a aucune raison pour quelqu&#8217;un d&#8217;acheter une fabrique de marteaux pour tous les types de marteaux.&#8221;</p>
<p>- &#8220;Oui, c&#8217;est sûr.&#8221;</p>
<p>- &#8220;Donc, à la place, on a commencé à vendre les plans de constructions de la fabrique de marteaux, afin que nos clients puissent construire leurs propres fabriques, complètement personnalisées pour produire uniquement les types de marteaux dont ils ont besoin.&#8221;</p>
<p>- &#8220;Laissez-moi deviner. Vous ne les vendez plus.&#8221;</p>
<p>- &#8220;Non. Bien entendu. Il se trouve que les gens ne veulent pas construire toute une fabrique juste pour faire quelques marteaux. Laissez la construction des fabriques aux experts de construction de fabriques, c&#8217;est ce que je dis toujours !!&#8221;</p>
<p>- &#8220;Et je vous approuve sur ce point.&#8221;</p>
<p>- &#8220;Et oui. Donc nous avons arrêté de vendre ces plans et nous avons commencé à vendre des fabriques de fabriques de marteaux. Chacune d&#8217;elle est construite par nos experts dans le business de fabrique de fabrique de marteaux, afin que vous n&#8217;ayez pas à vous inquiéter des détails triviaux de la construction d&#8217;une fabrique. Malgré cela, vous avez tous les bénéfices d&#8217;avoir votre propre fabrique personnalisée, produisant vos propres marteaux personnalisés, collant à vos designs spécifiques en matière de marteau.&#8221;</p>
<p>- &#8220;Heu, ça ne me semble pas vraiment&#8230;&#8221;</p>
<p>- &#8220;Je sais ce que vous allez dire !! &#8230; et nous ne les vendons d&#8217;ailleurs plus. Apparemment, peu de gens achetaient ces fabriques de fabrique de marteaux, donc nous avons trouvé une solution à ce problème.&#8221;</p>
<p>- &#8220;Hum.&#8221;</p>
<p>- &#8220;Nous avons pris le temps de faire le bilan de notre infrastructure technique, et nous avons déterminé que les gens développaient une frustration à avoir à gérer et opérer une fabrique de fabrique de marteaux, tout comme la fabrique qu&#8217;elle produisait. Ce genre de contrainte additionnelle peut se révéler fastidieux quand vous vous retrouvez dans un scénario où vous utilisez également une fabrique de fabrique de mètres, une fabrique de fabrique de scies et une fabrique de fabrique de niveaux. Sans compter un conglomérat de transformation du bois. Nous avons objectivement évalué la situation, et déterminé que c&#8217;était trop complexe pour quelqu&#8217;un qui voulait juste créer une étagère pour condiments&#8221;.</p>
<p>- &#8220;Non, sans blague ?&#8221;</p>
<p>- &#8220;Du coup cette semaine, nous mettons sur le marché une fabrique de fabrique de fabrique de création d&#8217;outils en tout genre, pour qu&#8217;ainsi vos différentes fabriques de fabrique à outils puissent être créées à partir d&#8217;une seule fabrique unifiée. La fabrique de fabrique de fabrique produira uniquement la fabrique de fabrique dont vous avez réellement besoin, et ainsi ces fabriques de fabrique produiront une seule fabrique basée sur vos spécifications d&#8217;outils personnalisés. Vous aurez *exactement* le marteau dont vous avez besoin, et exactement le bon mètre pour votre tâche, juste en appuyant sur un bouton (même si vous aurez probablement quelques fichiers de configuration pour que tout fonctionne selon vos attentes).</p>
<p>- &#8220;Donc, vous n&#8217;avez pas de marteaux ? Pas du tout ?&#8221;</p>
<p>- &#8220;Non. Si vous voulez vraiment une étagère à condiments de haute qualité, de standard industriel, vous avez vraiment besoin de quelque chose de plus sophistiqué qu&#8217;un simple marteau acheté à la quincaillerie du coin.&#8221;</p>
<p>- &#8220;Ok&#8230; Bon. Il faut ce qu&#8217;il faut. Si c&#8217;est comme ça qu&#8217;on fait maintenant, il faut bien que je m&#8217;y mette.&#8221;</p>
<p>- &#8220;Excellent !!&#8221;</p>
<p>- &#8220;Ça vient avec une documentation, pas vrai ?&#8221;</p>


feed_id: http://sametmax.com/?p=3730
title: RSS est une API
uri: RSS-est-une-API
url: http://sametmax.com/rss-est-une-api/
content:
<p>On a prédit la mort de RSS (et Atom que j&#8217;assimile ici) 500 fois déjà. C&#8217;est un truc de geek, personne l&#8217;utilise, gnagnagnagna.</p>
<p>Seulement RSS, ce n&#8217;est pas juste le truc qui me permet de faire ma veille informationelle tous les jours en 1 h plutôt que 6. C&#8217;est aussi une API standard qui répond aux critères suivants:</p>
<ul>
<li>paginable;</li>
<li>datée, et qui permet de récupérer les mises à jour depuis la dernière consultation;</li>
<li>stable: tout le monde sait comment ça marche, et ça ne bougera pas;</li>
<li>facilement débuggagble: il y a des tas de clients pour les humains;</li>
<li>interopérable: une chiée de services qui <a href="http://www.twittertorss.com/">gèrent</a>, transmettent, modifient ou <a href="http://sebsauvage.net/rhaa/index.php?2011/07/19/14/26/16-vroumvroum-">consomment du RSS</a>;</li>
<li>hyper simple: c&#8217;est du XML tout con, et en prime y a des centaines de <a href="http://pypi.python.org/pypi/feedparser/5.1.2">libs qui le gèrent</a>;</li>
<li>rapide à mettre en oeuvre: tout framework qui se respecte a une facilité pour <a href="https://docs.djangoproject.com/en/1.4/ref/contrib/syndication/">générer du RSS</a>;</li>
<li>on peut faire des <a href="http://thedeadone.net/blog/wordpress-tip-get-an-rss-feed-from-a-tag-and-from-a-search/">API chiadées</a>, pratiques et puissantes.</li>
</ul>
<p>Bref, RSS est un formidable outil pour les robots. Quand vous ne savez pas comment donner accès à votre site via une API, commencez par créer un flux RSS. Il en restera toujours quelque chose.</p>
<p>P.S: en écrivant cet article je me dis qu&#8217;il faudra peut être que j&#8217;écrive un article &#8220;Qu&#8217;est-ce que RSS et à quoi ça sert&#8221; parce que je suis sûr qu&#8217;il y a plein de gens à qui ça ne parle pas.</p>


feed_id: http://sametmax.com/?p=3741
title: Faire des enums en python
uri: Faire-des-enums-en-python
url: http://sametmax.com/faire-des-enums-en-python/
content:
<blockquote><p>Ceci est un post invité de <a href="http://recher.wordpress.com/" target="_blank">Réchèr </a>posté sous licence <a href="http://creativecommons.org/licenses/by/3.0/" target="_blank">creative common 3.0 unported</a>.</p></blockquote>
<p><em>&#8220;Moi, je viens du C++&#8221;</em></p>
<p>Voilà un propos qui fait classe. Ça donne un air de vieux de la vieille, à qui on ne la fait pas, et qui connaît des langages que c&#8217;est pas des langages de taffioles. &#8220;<em>De mon temps, fallait savoir ce qu&#8217;on faisait, sinon tout plantait. On ciselait notre code à la main dans des blocs de granit. Vous les gosses de maintenant, vous connaissez plus rien. Eh ! Sale jeune, au lieu d&#8217;importer des lib de feignasses, vient donc me changer ma poche à urine.</em>&#8221;</p>
<p>Ça aurait été encore plus classe de dire que je viens de l&#8217;Assembleur, mais je suis pas assez vieux pour ça. Et de toutes façons, en vrai, je viens du Pascal. Bref, passons.</p>
<p>Tout ça pour dire que dans le C++, il existe quelque chose que j&#8217;avais trouvé bien sympa : les enums.</p>
<h3>Comment ça marche ?</h3>
<p>Un enum est un type de variables ayant un domaine de valeur fixe et prédéfini, que l&#8217;on spécifie lors de la déclaration du type.</p>

<div class="wp_syntax"><div class="code"><pre class="c" style="font-family:monospace;"><span style="color: #993333;">typedef</span> <span style="color: #000000; font-weight: bold;">enum</span>
<span style="color: #009900;">&#123;</span>
     Pique<span style="color: #339933;">,</span>
     Coeur<span style="color: #339933;">,</span>
     Trefle<span style="color: #339933;">,</span>
     Carreau
<span style="color: #009900;">&#125;</span> ECouleursCartes<span style="color: #339933;">;</span></pre></div></div>

<p>Ensuite, on peut déclarer une variable de ce type, et lui affecter l&#8217;une des valeurs autorisées.</p>

<div class="wp_syntax"><div class="code"><pre class="c" style="font-family:monospace;">ECouleursCartes vMaCouleurCarte<span style="color: #339933;">;</span>
vMaCouleurCarte <span style="color: #339933;">=</span> Trefle<span style="color: #339933;">;</span></pre></div></div>

<p>Concrètement, chaque valeur correspond à un entier. Le compilateur fait les correspondances tout seul comme un grand.</p>
<h3>À quoi ça sert ?</h3>
<p>À avoir du code plus parlant quand on veut représenter des notions concrètes de la vraie vie, ou quand on implémente une machine à état. </p>
<p>Par exemple, vous créez une classe <code>FeuCirculation</code>. Vous avez besoin d&#8217;une variable renseignant sa couleur. Vous pouvez utiliser un int à l&#8217;arrache, et noter en commentaire quelque part : &#8220;0 c&#8217;est rouge, 1 c&#8217;est vert, 2 c&#8217;est orange.&#8221;. Mais c&#8217;est chiant. Il faut toujours garder en tête les correspondances. On risque d&#8217;attribuer des valeurs non documentées. Bref, y&#8217;a n&#8217;importe quoi dedans et ça pue, (un peu comme une poche à urine).</p>
<p>Avec un enum, tout est plus clair, aussi bien dans le code définissant la classe <code>FeuCirculation</code>, que dans le code qui l&#8217;utilise. Et c&#8217;est plus robuste.</p>
<p>L&#8217;exemple qui est donné très souvent dans les tutoriaux, c&#8217;est un enum <code>Animal</code>, contenant les valeurs <code>chien, chat, bœuf musqué, ...</code> Ça fonctionne, mais personnellement cet exemple me gêne un peu. Chaque animal est un objet à part entière. Dans ce cas, il vaudrait mieux créer une classe générique <code>Animal</code>, et la faire hériter. Ce qui permettra ensuite de créer des méthodes telles que <code>manger(), crier(), péter(), ...</code></p>
<p><a href="http://sametmax.com/faire-des-enums-en-python/fuck-a-duck/" rel="attachment wp-att-3744"><img src="http://sametmax.com/wp-content/uploads/2012/12/fuck-a-duck.jpg"?9d7bd4" alt="If it quacks like a duck, it may have noticed you are fucking it." title="If it quacks like a duck, it may have noticed you are fucking it." width="320" height="240" class="alignnone size-full wp-image-3744" /></a></p>
<p>Pour décrire plusieurs objets, utilisez des classes. Pour décrire les différents états d&#8217;un même objet, utilisez un enum. Pour décrire plusieurs objets simples, utilisez l&#8217;un ou l&#8217;autre, c&#8217;est à vous de choisir.</p>
<h3>Comment faire un enum en python ?</h3>
<p>Il n&#8217;y a, à ma connaissance, pas de structure syntaxique dédiée. Mais c&#8217;est pas grave, on va bien trouver quelque chose.</p>
<p>Le plus simple, pour commencer, c&#8217;est de garder l&#8217;idée de la correspondance avec des entiers. Ça offre plein d&#8217;avantages :</p>
<ul>
<li>On sait exactement comment ça marche à l&#8217;intérieur.</li>
<li>On peut très facilement enregistrer des enums dans un fichier ou une base de donnée, puisque ce ne sont que des nombres.</li>
<li>On peut ordonner les valeurs. À utiliser avec prudence, car ça n&#8217;a pas toujours de sens. (Dire que l&#8217;état &#8220;feu rouge&#8221; est inférieur à l&#8217;état &#8220;feu vert&#8221;, qu&#8217;est-ce que cela signifie exactement ?)</li>
</ul>
<p>La première idée qui vient à l&#8217;esprit, c&#8217;est de créer une classe avec les valeurs dedans, et de ne plus jamais les changer par la suite.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #808080; font-style: italic;"># On l'appelle FeuCirculation et non pas FeuRouge. </span>
<span style="color: #808080; font-style: italic;"># Parce qu'un feu n'est pas forcément rouge.</span>
<span style="color: #808080; font-style: italic;"># (Putain de langue française à la con qui fait n'importe quoi).</span>
<span style="color: #ff7700;font-weight:bold;">class</span> FeuCirculation:
    ROUGE = <span style="color: #ff4500;">0</span>
    ORANGE = <span style="color: #ff4500;">1</span>
    VERT = <span style="color: #ff4500;">2</span>
    ORANGE_CLIGNOTANT = <span style="color: #ff4500;">3</span>
    TOUT_ETEINT = <span style="color: #ff4500;">4</span>
&nbsp;
feuActuel = FeuCirculation.<span style="color: black;">ORANGE</span></pre></div></div>

<p>C&#8217;est bien, mais chiant à maintenir. Si on veut ajouter un autre état (par exemple, <code>FLECHE_DROITE_ORANGE_CLIGNOTANTE</code>), et qu&#8217;on se plante dans les valeurs numériques, il y a un risque d&#8217;avoir des doublons, et ça fiche tout en l&#8217;air.</p>
<p>Voici un petit peu mieux :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #ff7700;font-weight:bold;">class</span> FeuCirculation:
    <span style="color: black;">&#40;</span>ROUGE,
     ORANGE,
     VERT,
     ORANGE_CLIGNOTANT,
     TOUT_ETEINT,
    <span style="color: black;">&#41;</span> = <span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">5</span><span style="color: black;">&#41;</span></pre></div></div>

<p><code>range(5)</code> renvoie un tuple (0, 1, 2, 3, 4). Des entiers différents sont attribués aux valeurs de l&#8217;enum. Si on veut en rajouter une et qu&#8217;on oublie de remplacer <code>range(5)</code> par <code>range(6)</code>, ça va balancer une exception. Tout va bien.</p>
<p>Au cas où vous demanderiez : &#8220;qu&#8217;est-ce qui m&#8217;empêche de redéfinir l&#8217;une des valeurs, à un autre endroit du code, et de foutre le bordel ?&#8221;, je répondrais <em>&#8220;We are all consenting adults here&#8221;</em>. (Se référer à la philosophie du python. Si besoin, ce sera l&#8217;occasion d&#8217;un autre article).</p>
<p><a href="http://sametmax.com/wp-content/uploads/2012/12/Lexxxi_Luxe_Sapphire_Cotton_Candi_2394hsp_10.jpg"?9d7bd4"><img src="http://sametmax.com/wp-content/uploads/2012/12/Lexxxi_Luxe_Sapphire_Cotton_Candi_2394hsp_10.jpg"?9d7bd4" alt="Some consenting adults. (Je peux venir ?)" title="Some consenting adults. (Je peux venir ?)" width="375" height="250" class="alignnone size-full wp-image-3765" /></a></p>
<h3>Le code est beau, mais pour débugger ?</h3>
<p>C&#8217;est un peu lourdingue. Lorsqu&#8217;on fait <code>print feuActuel</code> (ou lorsqu&#8217;on tape directement <code>feuActuel</code> dans <a href="http://sametmax.com/debugger-en-python-les-bases-de-pdb/" target="_blank">une console pdb</a>), c&#8217;est une valeur numérique pas claire qui va s&#8217;afficher, au lieu d&#8217;un joli &#8220;ORANGE&#8221;, &#8220;ROUGE&#8221;, &#8230;</p>
<p>Un petit dictionnaire de correspondance &#8220;valeur numérique&#8221; -> &#8220;nom à afficher&#8221; serait de bon aloi. Quelque chose de ce genre, à placer dans la définiton de la classe <code>FeuCirculation </code>:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">    dictReverse = <span style="color: black;">&#123;</span>
        ROUGE : <span style="color: #483d8b;">&quot;ROUGE&quot;</span>,
        ORANGE : <span style="color: #483d8b;">&quot;ORANGE&quot;</span>,
        VERT : <span style="color: #483d8b;">&quot;VERT&quot;</span>,
        ORANGE_CLIGNOTANT : <span style="color: #483d8b;">&quot;ORANGE_CLIGNOTANT&quot;</span>,
        TOUT_ETEINT : <span style="color: #483d8b;">&quot;TOUT_ETEINT&quot;</span>,
    <span style="color: black;">&#125;</span></pre></div></div>

<p>Fort bien. Mais n&#8217;est-ce pas un peu casse-couille ? Eh si. Des répétitions à la pelle, et dictReverse doit rester synchro avec les définitions des valeurs. C&#8217;est redevenu chiant à maintenir.</p>
<p><a href="http://sametmax.com/wp-content/uploads/2012/12/dick_rivers2.jpg"?9d7bd4"><img src="http://sametmax.com/wp-content/uploads/2012/12/dick_rivers2.jpg"?9d7bd4" alt="Hey, je suis Dict-Reverse, et je suis chiant à maintenir. bi-boppe eu loulaaaa." title="Hey, je suis Dict-Reverse, et je suis chiant à maintenir. bi-boppe eu loulaaaa." width="240" height="333" class="alignnone size-full wp-image-3766" /></a></p>
<h3>Définition dynamique de nouveaux types</h3>
<p>Soyons franc, j&#8217;ai piqué cette astuce ici :<br />
<a href="http://stackoverflow.com/questions/36932/whats-the-best-way-to-implement-an-enum-in-python" target="_blank">http://stackoverflow.com/questions/36932/whats-the-best-way-to-implement-an-enum-in-python</a></p>
<p>Vous connaissez certainement déjà la fonction native <code>type()</code>. Elle renvoie le type du truc passé en paramètre. Youpi.</p>
<p>Mais saviez-vous qu&#8217;elle permet également de créer de nouveaux types ? Pour ce faire, il faut l&#8217;appeler avec 3 paramètres : </p>
<ul>
<li>Le nom.</li>
<li>Une liste indiquant les types de base (dans le cas où on veut que le type soit hérité).</li>
<li>Un dictionnaire contenant les attributs. Les clés sont des chaînes de caractère, et correspondront aux noms des attributs.</li>
</ul>
<p>La création de l&#8217;enum <code>FeuCirculation </code>pourrait donc se faire de cette manière :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">FeuCirculation = <span style="color: #008000;">type</span><span style="color: black;">&#40;</span>
    <span style="color: #483d8b;">&quot;FeuCirculation&quot;</span>,
    <span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>,
    <span style="color: black;">&#123;</span>
        <span style="color: #483d8b;">&quot;ROUGE&quot;</span> : <span style="color: #ff4500;">0</span>, 
        <span style="color: #483d8b;">&quot;ORANGE&quot;</span> : <span style="color: #ff4500;">1</span>, 
        <span style="color: #483d8b;">&quot;VERT&quot;</span> : <span style="color: #ff4500;">2</span>, 
        <span style="color: #483d8b;">&quot;ORANGE_CLIGNOTANT&quot;</span> : <span style="color: #ff4500;">3</span>, 
        <span style="color: #483d8b;">&quot;TOUT_ETEINT&quot;</span> : <span style="color: #ff4500;">4</span>
    <span style="color: black;">&#125;</span><span style="color: black;">&#41;</span>
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> FeuCirculation
<span style="color: #66cc66;">&lt;</span>class <span style="color: #483d8b;">'__main__.FeuCirculation'</span><span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> FeuCirculation.<span style="color: black;">VERT</span>
<span style="color: #ff4500;">2</span></pre></div></div>

<p>On peut également ajouter le dictReverse dans le dictionnaire des attributs. (Ça fait un dictionnaire dans un dictionnaire, c&#8217;est lol).</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">FeuCirculation = <span style="color: #008000;">type</span><span style="color: black;">&#40;</span>
    <span style="color: #483d8b;">&quot;FeuCirculation&quot;</span>,
    <span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>,
    <span style="color: black;">&#123;</span>
        <span style="color: #483d8b;">&quot;ROUGE&quot;</span> : <span style="color: #ff4500;">0</span>,
        <span style="color: #483d8b;">&quot;ORANGE&quot;</span> : <span style="color: #ff4500;">1</span>,
        <span style="color: #483d8b;">&quot;VERT&quot;</span> : <span style="color: #ff4500;">2</span>,
        <span style="color: #483d8b;">&quot;ORANGE_CLIGNOTANT&quot;</span> : <span style="color: #ff4500;">3</span>,
        <span style="color: #483d8b;">&quot;TOUT_ETEINT&quot;</span> : <span style="color: #ff4500;">4</span>,
        <span style="color: #483d8b;">&quot;dictReverse&quot;</span> : <span style="color: black;">&#123;</span>
            <span style="color: #ff4500;">0</span> : <span style="color: #483d8b;">&quot;ROUGE&quot;</span>,
            <span style="color: #ff4500;">1</span> : <span style="color: #483d8b;">&quot;ORANGE&quot;</span>,
            <span style="color: #ff4500;">2</span> : <span style="color: #483d8b;">&quot;VERT&quot;</span>,
            <span style="color: #ff4500;">3</span> : <span style="color: #483d8b;">&quot;ORANGE_CLIGNOTANT&quot;</span>,
            <span style="color: #ff4500;">4</span> : <span style="color: #483d8b;">&quot;TOUT_ETEINT&quot;</span><span style="color: black;">&#125;</span>
    <span style="color: black;">&#125;</span><span style="color: black;">&#41;</span>
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> FeuCirculation
<span style="color: #66cc66;">&lt;</span>class <span style="color: #483d8b;">'__main__.FeuCirculation'</span><span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> feuxActuel = FeuCirculation.<span style="color: black;">VERT</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> feuxActuel
<span style="color: #ff4500;">2</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> FeuCirculation.<span style="color: black;">dictReverse</span><span style="color: black;">&#91;</span>feuxActuel<span style="color: black;">&#93;</span>
<span style="color: #483d8b;">'VERT'</span></pre></div></div>

<p>Et maintenant y&#8217;a plus qu&#8217;à coder une petite fonction qui fait tout ça génériquement.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #ff7700;font-weight:bold;">def</span> enum<span style="color: black;">&#40;</span>enumName, <span style="color: #66cc66;">*</span>listValueNames<span style="color: black;">&#41;</span>:
    <span style="color: #808080; font-style: italic;"># Une suite d'entiers, on en crée autant</span>
    <span style="color: #808080; font-style: italic;"># qu'il y a de valeurs dans l'enum.</span>
    listValueNumbers = <span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #008000;">len</span><span style="color: black;">&#40;</span>listValueNames<span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>
    <span style="color: #808080; font-style: italic;"># création du dictionaire des attributs.</span>
    <span style="color: #808080; font-style: italic;"># Remplissage initial avec les correspondances : valeur d'enum -&gt; entier</span>
    dictAttrib = <span style="color: #008000;">dict</span><span style="color: black;">&#40;</span> <span style="color: #008000;">zip</span><span style="color: black;">&#40;</span>listValueNames, listValueNumbers<span style="color: black;">&#41;</span> <span style="color: black;">&#41;</span>
    <span style="color: #808080; font-style: italic;"># création du dictionnaire inverse. entier -&gt; valeur d'enum</span>
    dictReverse = <span style="color: #008000;">dict</span><span style="color: black;">&#40;</span> <span style="color: #008000;">zip</span><span style="color: black;">&#40;</span>listValueNumbers, listValueNames<span style="color: black;">&#41;</span> <span style="color: black;">&#41;</span>
    <span style="color: #808080; font-style: italic;"># ajout du dictionnaire inverse dans les attributs</span>
    dictAttrib<span style="color: black;">&#91;</span><span style="color: #483d8b;">&quot;dictReverse&quot;</span><span style="color: black;">&#93;</span> = dictReverse
    <span style="color: #808080; font-style: italic;"># création et renvoyage du type</span>
    mainType = <span style="color: #008000;">type</span><span style="color: black;">&#40;</span>enumName, <span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>, dictAttrib<span style="color: black;">&#41;</span>
    <span style="color: #ff7700;font-weight:bold;">return</span> mainType
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> FeuCirculation = enum<span style="color: black;">&#40;</span>
        <span style="color: #483d8b;">&quot;FeuCirculation&quot;</span>,
        <span style="color: #483d8b;">&quot;ROUGE&quot;</span>, <span style="color: #483d8b;">&quot;ORANGE&quot;</span>, <span style="color: #483d8b;">&quot;VERT&quot;</span>,
        <span style="color: #483d8b;">&quot;ORANGE_CLIGNOTANT&quot;</span>, <span style="color: #483d8b;">&quot;TOUT_ETEINT&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> FeuCirculation.<span style="color: black;">TOUT_ETEINT</span>
<span style="color: #ff4500;">4</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> FeuCirculation.<span style="color: black;">dictReverse</span><span style="color: black;">&#91;</span>FeuCirculation.<span style="color: black;">TOUT_ETEINT</span><span style="color: black;">&#93;</span>
<span style="color: #483d8b;">'TOUT_ETEINT'</span></pre></div></div>

<p>Une petite précision : d&#8217;habitude, quand on crée des classes ou des types, c&#8217;est pour les instancier. Là on ne le fait pas, on se contente d&#8217;utiliser des valeurs statiques contenues dans le type. Vous pourriez faire <code>feuDuCarrefour = FeuCirculation()</code>. Ça va fonctionner, mais ça ne vous servira à rien.</p>
<p><a href="http://sametmax.com/wp-content/uploads/2012/12/weird_stuff_cool_crazy_offbeat_traffic-light-tree-06_200907241442222897.jpg"?9d7bd4"><img src="http://sametmax.com/wp-content/uploads/2012/12/weird_stuff_cool_crazy_offbeat_traffic-light-tree-06_200907241442222897.jpg"?9d7bd4" alt="Le code de la route a parfois besoin de refactoring" title="Le code de la route a parfois besoin de refactoring" width="400" height="300" class="alignnone size-full wp-image-3767" /></a></p>
<h3>Mais si on mélange les enums ?</h3>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> FeuCirculation = enum<span style="color: black;">&#40;</span>
        <span style="color: #483d8b;">&quot;FeuCirculation&quot;</span>,
        <span style="color: #483d8b;">&quot;ROUGE&quot;</span>, <span style="color: #483d8b;">&quot;ORANGE&quot;</span>, <span style="color: #483d8b;">&quot;VERT&quot;</span>,
        <span style="color: #483d8b;">&quot;ORANGE_CLIGNOTANT&quot;</span>, <span style="color: #483d8b;">&quot;TOUT_ETEINT&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> etatMatiere = enum<span style="color: black;">&#40;</span>
        <span style="color: #483d8b;">&quot;etatMatiere&quot;</span>, 
        <span style="color: #483d8b;">&quot;SOLIDE&quot;</span>, <span style="color: #483d8b;">&quot;LIQUIDE&quot;</span>, <span style="color: #483d8b;">&quot;GAZEUX&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> etatMatiere.<span style="color: black;">dictReverse</span><span style="color: black;">&#91;</span>FeuCirculation.<span style="color: black;">VERT</span><span style="color: black;">&#93;</span>
<span style="color: #483d8b;">'GAZEUX'</span></pre></div></div>

<p>Mince alors. Ça fait n&#8217;importe quoi, sans signaler aucune erreur. C&#8217;est normal. D&#8217;un enum à l&#8217;autre, on ne fait que manipuler des entiers, qui restent les mêmes. Les correspondances se font joyeusement, même si ça n&#8217;a aucun sens. Dans le même ordre d&#8217;idée : <code>FeuCirculation.ROUGE == etatMatiere.SOLIDE</code> renverra <code>True</code>, ce qui ne veut rien dire. Comment régler ce problème ?</p>
<p><a href="http://sametmax.com/wp-content/uploads/2012/12/iced_traffic_lights.jpg"?9d7bd4"><img src="http://sametmax.com/wp-content/uploads/2012/12/iced_traffic_lights.jpg"?9d7bd4" alt="Better have traffic ice than traffic jam." title="Better have traffic ice than traffic jam." width="426" height="284" class="alignnone size-full wp-image-3772" /></a></p>
<h3>Solution 1 : ne pas régler le problème</h3>
<p><em>&#8220;We are all consenting adults here&#8221;</em>, on ne va donc pas compliquer le code en rajoutant des sécurités de partout, sous prétexte d&#8217;empêcher des erreurs. Le seule moyen valable de se prémunir de faire n&#8217;importe quoi quand on code, c&#8217;est tout bêtement de rester concentré et de faire gaffe à ce qu&#8217;on fait.</p>
<p>Honnêtement, ça ne m&#8217;est jamais arrivé de mélanger des enums entre eux. Pourtant, je n&#8217;ai pas la prétention de tout faire juste et sans bugs du premier coup. Parmi mes bourdes préférées : copier-coller la ligne du dessus et ne pas faire les bons remplacements (les &#8220;x&#8221; par des &#8220;y&#8221;, les &#8220;1&#8243; par des &#8220;2&#8243;, etc.), ou encore : déclarer une fonction, lui faire renvoyer un résultat bidon parce que je préfère la coder plus tard, et oublier que je ne l&#8217;ai pas codé.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #ff7700;font-weight:bold;">def</span> calculDist<span style="color: black;">&#40;</span>point1, point2<span style="color: black;">&#41;</span>:
    distX = point1.<span style="color: black;">x</span> - point1.<span style="color: black;">x</span>
    distY = point2.<span style="color: black;">x</span> - point2.<span style="color: black;">x</span>
    <span style="color: #ff7700;font-weight:bold;">return</span> <span style="color: #dc143c;">math</span>.<span style="color: black;">sqrt</span><span style="color: black;">&#40;</span>distX <span style="color: #66cc66;">*</span> distX + distY <span style="color: #66cc66;">*</span> distY<span style="color: black;">&#41;</span>
    <span style="color: #808080; font-style: italic;"># ami lecteur, sauras-tu trouver tous les fails</span>
    <span style="color: #808080; font-style: italic;"># présents dans cette fonction ?</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">def</span> RemoveDoubleLetters<span style="color: black;">&#40;</span>strValue<span style="color: black;">&#41;</span>:
    <span style="color: #808080; font-style: italic;"># TODO : coder le truc. Mais là, j'ai la flemme.</span>
    <span style="color: #ff7700;font-weight:bold;">return</span> strValue</pre></div></div>

<p><a href="http://sametmax.com/wp-content/uploads/2012/12/bsod.jpg"?9d7bd4"><img src="http://sametmax.com/wp-content/uploads/2012/12/bsod.jpg"?9d7bd4" alt="BSOD !!" title="BSOD !!" width="351" height="461" class="alignnone size-full wp-image-3773" /></a></p>
<p>Pour limiter les risques de mélange, voici quelques conseils :</p>
<ul>
<li>Préfixez les variables contenant une valeur d&#8217;enum : <code>feu</code> pour <code>FeuCirculation</code>, <code>emat</code> pour <code>etatMatiere</code>, etc. De cette manière, les erreurs de code sautent aux yeux. (<a href="http://www.joelonsoftware.com/articles/Wrong.html" target="_blank">making wrong code look wrong</a>, tout ça&#8230;)
</li>
<li>Il est important de ne pas polluer inutilement l&#8217;espace de nommage. Dans un fichier donné, n&#8217;importez pas les enums dont vous n&#8217;avez pas besoin. De cette manière, une erreur sera renvoyée si jamais vous utilisez une valeur d&#8217;enum imprévue. Je doute que vous ayez besoin, dans un même fichier de code, de renseigner des états de feux rouge et des états de matière.
</li>
<li>Si vous faites exprès de mélanger des enums, en pensant que vous n&#8217;avez aucun moyen de faire autrement, c&#8217;est qu&#8217;il y a, dès l&#8217;origine, un problème de conception dans votre code.</li>
</ul>
<p><a href="http://sametmax.com/wp-content/uploads/2012/12/cabrel.jpg"?9d7bd4"><img src="http://sametmax.com/wp-content/uploads/2012/12/cabrel.jpg"?9d7bd4" alt="Vieng fayre toi-même leu mélainge des enums, sur les muuuurs deu la cabaneu du côdeur. Vieng t&#039;assouar." title="Vieng fayre toi-même leu mélainge des enums, sur les muuuurs deu la cabaneu du côdeur. Vieng t&#039;assouar." width="350" height="238" class="alignnone size-full wp-image-3774" /></a></p>
<h3>Solution 2 : des enums fortement typés.</h3>
<p>Au lieu que les valeurs internes des enums soient de simples entiers, on crée un type pour chacune d&#8217;elle. Comme ça, on est sûr que ça renverra une erreur si on se confusionne. Par contre, on perd en simplicité, et ce n&#8217;est plus aussi simple pour la sérialisation.</p>
<p>Soyons fous, et voyons ce que ça donne !</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #ff7700;font-weight:bold;">def</span> strongTypedEnum<span style="color: black;">&#40;</span>enumName, <span style="color: #66cc66;">*</span>listValueNames<span style="color: black;">&#41;</span>:
    <span style="color: #808080; font-style: italic;"># création d'une liste de type. sans attribut, sans héritage.</span>
    <span style="color: #808080; font-style: italic;"># le nom du type est composé du nom de l'enum et du nom de la valeur,</span>
    <span style="color: #808080; font-style: italic;"># séparés par un point.</span>
    listValueTyped = <span style="color: black;">&#91;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;.&quot;</span>.<span style="color: black;">join</span><span style="color: black;">&#40;</span><span style="color: black;">&#40;</span>enumName, nameValue<span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>, <span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>, <span style="color: black;">&#123;</span><span style="color: black;">&#125;</span><span style="color: black;">&#41;</span>
                       <span style="color: #ff7700;font-weight:bold;">for</span> nameValue <span style="color: #ff7700;font-weight:bold;">in</span> listValueNames <span style="color: black;">&#93;</span>
    <span style="color: #808080; font-style: italic;"># Ensuite, c'est tout pareil que la fonction d'avant.</span>
    dictAttrib = <span style="color: #008000;">dict</span><span style="color: black;">&#40;</span> <span style="color: #008000;">zip</span><span style="color: black;">&#40;</span>listValueNames, listValueTyped<span style="color: black;">&#41;</span> <span style="color: black;">&#41;</span>
    dictReverse = <span style="color: #008000;">dict</span><span style="color: black;">&#40;</span> <span style="color: #008000;">zip</span><span style="color: black;">&#40;</span>listValueTyped, listValueNames<span style="color: black;">&#41;</span> <span style="color: black;">&#41;</span>
    dictAttrib<span style="color: black;">&#91;</span><span style="color: #483d8b;">&quot;dictReverse&quot;</span><span style="color: black;">&#93;</span> = dictReverse
    mainType = <span style="color: #008000;">type</span><span style="color: black;">&#40;</span>enumName, <span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>, dictAttrib<span style="color: black;">&#41;</span>
    <span style="color: #ff7700;font-weight:bold;">return</span> mainType
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> FeuCirculation = strongTypedEnum<span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;FeuCirculation&quot;</span>,
        <span style="color: #483d8b;">&quot;ROUGE&quot;</span>, <span style="color: #483d8b;">&quot;ORANGE&quot;</span>, <span style="color: #483d8b;">&quot;VERT&quot;</span>,
        <span style="color: #483d8b;">&quot;ORANGE_CLIGNOTANT&quot;</span>, <span style="color: #483d8b;">&quot;TOUT_ETEINT&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> etatMatiere = strongTypedEnum<span style="color: black;">&#40;</span>
        <span style="color: #483d8b;">&quot;etatMatiere&quot;</span>, 
        <span style="color: #483d8b;">&quot;SOLIDE&quot;</span>, <span style="color: #483d8b;">&quot;LIQUIDE&quot;</span>, <span style="color: #483d8b;">&quot;GAZEUX&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> etatMatiere.<span style="color: black;">LIQUIDE</span>
<span style="color: #66cc66;">&lt;</span>class <span style="color: #483d8b;">'__main__.etatMatiere.LIQUIDE'</span><span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> etatMatiere.<span style="color: black;">dictReverse</span><span style="color: black;">&#91;</span>FeuCirculation.<span style="color: black;">ROUGE</span><span style="color: black;">&#93;</span>
Traceback <span style="color: black;">&#40;</span>most recent call last<span style="color: black;">&#41;</span>:
  File <span style="color: #483d8b;">&quot;&lt;pyshell#20&gt;&quot;</span>, line <span style="color: #ff4500;">1</span>, <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #66cc66;">&lt;</span>module<span style="color: #66cc66;">&gt;</span>
    etatMatiere.<span style="color: black;">dictReverse</span><span style="color: black;">&#91;</span>FeuCirculation.<span style="color: black;">ROUGE</span><span style="color: black;">&#93;</span>
<span style="color: #008000;">KeyError</span>: <span style="color: #66cc66;">&lt;</span>class <span style="color: #483d8b;">'__main__.FeuCirculation.ROUGE'</span><span style="color: #66cc66;">&gt;</span></pre></div></div>

<p>Mais est-ce bien nécessaire ?</p>
<h3>Y&#8217;a une lib pour ça</h3>
<p>Comme toujours, avec cette foutue prolifération de code libre, dès que quelque chose de cool peut potentiellement exister, un connard de geek l&#8217;a déjà fait, vous privant de l&#8217;occasion de le faire vous-même et de retirer la gloire qui en décombe. <a href="http://packages.python.org/flufl.enum/README.html" target="_blank">La lib flufl.enum</a> permet donc de créer et manipuler des enums, avec autant et même plus de fonctionnalités que ce que je viens de décrire ici. (Connards de geeks qui viennent manger le pain des français).</p>
<p>Par contre, j&#8217;ai regardé le code, et j&#8217;ai pas pigé comment ça fonctionnait à l&#8217;intérieur. Ça fera peut-être l&#8217;objet d&#8217;un autre article, si j&#8217;ai le courage de me plonger dedans, et que je trouve ça intéressant et rigolo.</p>
<p>De toutes façons, les libs c&#8217;est chiant, ça ajoute des dépendances, <a href="http://sametmax.com/vous-en-pensez-quoi-de-cette-idee/" target="_blank">il vaut mieux tout coder à la main</a>.</p>
<h3>Disgression 1 : quelle classe ce type !</h3>
<p>Déclarer un type avec la fonction <code>type()</code>, et déclarer une classe, ça ne fait pas exactement la même chose.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">class</span> MaClasse:
	<span style="color: #ff7700;font-weight:bold;">pass</span>
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> MaClasse
<span style="color: #66cc66;">&lt;</span>class <span style="color: #dc143c;">__main__</span>.<span style="color: black;">MaClasse</span> at 0x011CB270<span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> instanceClasse = MaClasse<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> instanceClasse
<span style="color: #66cc66;">&lt;</span>__main__.<span style="color: black;">MaClasse</span> instance at 0x011C8BC0<span style="color: #66cc66;">&gt;</span>
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> MonType = <span style="color: #008000;">type</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;Le_Nom_De_Mon_Type&quot;</span>, <span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>, <span style="color: black;">&#123;</span><span style="color: black;">&#125;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> MonType
<span style="color: #66cc66;">&lt;</span>class <span style="color: #483d8b;">'__main__.Le_Nom_De_Mon_Type'</span><span style="color: #66cc66;">&gt;</span>
<span style="color: #808080; font-style: italic;"># Hey ! Le nom est dans une string, et y'a pas d'adresse mémoire !</span>
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> instanceType = MonType<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> instanceType
<span style="color: #66cc66;">&lt;</span>__main__.<span style="color: black;">Le_Nom_De_Mon_Type</span> <span style="color: #008000;">object</span> at 0x011C1B30<span style="color: #66cc66;">&gt;</span>
<span style="color: #808080; font-style: italic;"># Hey ! C'est un object, et pas une instance !</span></pre></div></div>

<p>Ça a peut-être quelque chose à voir avec une histoire de old-style class et new-style class. J&#8217;ai pas cherché plus loin pour l&#8217;instant. Ça fera peut-être l&#8217;objet d&#8217;un autre-autre article, si j&#8217;ai le courage de me plonger dedans, et que je trouve ça intéressant et rigolo.</p>
<h3>Disgression 2 : Restons dans les règles</h3>
<p>J&#8217;avais trouvé un autre exemple de machine à état, plus rigolo que des feux de circulation ou de la matière. Je ne m&#8217;en suis pas servi durant mes explications, parce que ça aurait distrait le lecteur / la lectrice (<a href="http://sametmax.com/bien-expliquer-quelque-chose-les-regles-de-base/" target="_blank">charge cérébrale</a>, tout ça&#8230;). Mais ce serait vraiment dommage de ne pas vous en faire profiter. Le voici donc :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> PhaseCycleUterin = enum<span style="color: black;">&#40;</span>
        <span style="color: #483d8b;">&quot;PhaseCycleUterin&quot;</span>,
        <span style="color: #483d8b;">&quot;PREPUBERE&quot;</span>, <span style="color: #483d8b;">&quot;MENSTRUELLE&quot;</span>, 
        <span style="color: #483d8b;">&quot;OVULATION&quot;</span>, <span style="color: #483d8b;">&quot;PROLIPERATIVE&quot;</span>, <span style="color: #483d8b;">&quot;SECRETRICE&quot;</span>
        <span style="color: #483d8b;">&quot;ENCEINTE&quot;</span>, <span style="color: #483d8b;">&quot;MENOPAUSE&quot;</span><span style="color: black;">&#41;</span>
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> etatMatiere.<span style="color: black;">dictReverse</span><span style="color: black;">&#91;</span>PhaseCycleUterin.<span style="color: black;">MENSTRUELLE</span><span style="color: black;">&#93;</span>
<span style="color: #483d8b;">'LIQUIDE'</span></pre></div></div>

<p>Voilà, ce sera tout pour aujourd&#8217;hui. La prochaine fois, nous redéfinirons le type &#8220;object&#8221; en utilisant uniquement les picots du langage Braille.</p>
<p><a href="http://sametmax.com/wp-content/uploads/2012/12/femme_avec_regles.jpg"?9d7bd4"><img src="http://sametmax.com/wp-content/uploads/2012/12/femme_avec_regles.jpg"?9d7bd4" alt="Une femme qui a ses règles." title="Une femme qui a ses règles." width="470" height="671" class="alignnone size-full wp-image-3775" /></a></p>


feed_id: http://sametmax.com/?p=3562
title: Implémenter une fenêtre glissante en Python avec un deque
uri: Implémenter-une-fenêtre-glissante-en-Python-avec-un-deque
url: http://sametmax.com/implementer-une-fenetre-glissante-en-python-avec-un-deque/
content:
<p>Quand j&#8217;entends deque, je pense plus à un deck de Magic de Gathering qu&#8217;à un module Python, mais aujourd&#8217;hui j&#8217;utilise beaucoup plus le dernier que le précédent.</p>
<p>On a déjà vu comment implémenter <a href="http://sametmax.com/parcourir-un-iterable-par-morceaux-en-python/">l&#8217;itération par morceaux </a>sur un itérable de n&#8217;importe quelle taille. Grâce au deque, on peut aussi facilement créer une fenêtre glissante.</p>
<h2>Qu&#8217;est-ce qu&#8217;une fenêtre glissante ?</h2>
<p>Il s&#8217;agit de parcourir un itérable par tranches de &#8220;n&#8221; élements, en faisant en sorte que l&#8217;insertion d&#8217;un nouvel élément dans la tranche implique la supression du premier entré. Mouai, dit comme ça c&#8217;est pas clair. Un p&#8217;tit exemple ?</p>
<p>Fenêtre glissante de 3 éléments sur une liste de 10 éléments, à la mano:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> l = <span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">10</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l
<span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span>, <span style="color: #ff4500;">6</span>, <span style="color: #ff4500;">7</span>, <span style="color: #ff4500;">8</span>, <span style="color: #ff4500;">9</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span>:<span style="color: #ff4500;">3</span><span style="color: black;">&#93;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span><span style="color: #ff4500;">1</span>:<span style="color: #ff4500;">4</span><span style="color: black;">&#93;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span><span style="color: #ff4500;">2</span>:<span style="color: #ff4500;">5</span><span style="color: black;">&#93;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span><span style="color: #ff4500;">3</span>:<span style="color: #ff4500;">6</span><span style="color: black;">&#93;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span><span style="color: black;">&#93;</span>
...</pre></div></div>

<p>A ne pas confondre avec le parcours par morceaux, qu&#8217;on déjà traité, et qui donne ça:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span>, <span style="color: #ff4500;">6</span>, <span style="color: #ff4500;">7</span>, <span style="color: #ff4500;">8</span>, <span style="color: #ff4500;">9</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>:<span style="color: #ff4500;">3</span><span style="color: black;">&#93;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span><span style="color: #ff4500;">3</span>:<span style="color: #ff4500;">6</span><span style="color: black;">&#93;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span><span style="color: #ff4500;">6</span>:<span style="color: #ff4500;">9</span><span style="color: black;">&#93;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">6</span>, <span style="color: #ff4500;">7</span>, <span style="color: #ff4500;">8</span><span style="color: black;">&#93;</span>
...</pre></div></div>

<p>Et bien sûr, comme d&#8217;hab, vous allez dire &#8220;Cher Sam, malgré ton génie qui n&#8217;a d&#8217;égal que ta beauté et l&#8217;incohérence de cette remarque, je ne vois pas vraiment à quoi ça sert.&#8221;</p>
<p>Et bien essentiellement dans les situations où un élément est dépendant des précédents, par exemple pour répondre à des questions existentielles comme &#8220;quel est le premier élément qui est la somme des 5 le précédant dans cette liste ?&#8221;. Ça n&#8217;arrive certes pas tous les jours, mais fuck, j&#8217;avais pas de meilleur exemple en tête, là, tout de suite.</p>
<h2>Qu&#8217;est-ce qu&#8217;un deque ?</h2>
<p>Un <a href="http://docs.python.org/2.7/library/collections.html">deque</a> est une structure de données qui permet d&#8217;implémenter des comportements de types piles, files, FIFO, LIFO, et autres pipos avec efficacité. Traduit en langage de tous les jours, c&#8217;est comme une liste, mais:</p>
<ul>
<li>ajouter un élément à la fin ou au début est une opération super rapide;</li>
<li>les retirer aussi;</li>
<li>on peut itérer dessus à la même vitesse que la liste;</li>
<li>mais accéder à un élement qui n&#8217;est pas au début ou à la fin juste par son index est très lent;</li>
<li>on peut limiter le nombre d&#8217;éléments que ça contient automatiquement.</li>
</ul>
<p>On va donc l&#8217;utiliser comme acumulateur ou pour faire des files d&#8217;attentes.</p>
<p>Démonstration:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">collections</span> <span style="color: #ff7700;font-weight:bold;">import</span> deque
<span style="color: #66cc66;">&gt;&gt;&gt;</span> ze_deck = deque<span style="color: black;">&#40;</span>maxlen=<span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># on limite le deque à 3 éléments</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> ze_deck.<span style="color: black;">append</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> ze_deck
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">1</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> ze_deck.<span style="color: black;">append</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> ze_deck
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> ze_deck.<span style="color: black;">append</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> ze_deck
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> ze_deck.<span style="color: black;">append</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">4</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># ... et MAGIQUEMENT !</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> ze_deck
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> ze_deck:
...     <span style="color: #ff7700;font-weight:bold;">print</span> x
...     
<span style="color: #ff4500;">2</span>
<span style="color: #ff4500;">3</span>
<span style="color: #ff4500;">4</span></pre></div></div>

<p>Bam le dernier élément est squizzé, et tout ça rapidement et efficacement. Vous voyez où je veux subtilement en venir ?</p>
<h2>Et finalement: comment on utilise l&#8217;un pour faire l&#8217;autre ?</h2>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">collections</span> <span style="color: #ff7700;font-weight:bold;">import</span> deque
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">itertools</span> <span style="color: #ff7700;font-weight:bold;">import</span> islice
<span style="color: #66cc66;">&gt;&gt;&gt;</span> 
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">def</span> window<span style="color: black;">&#40;</span>iterable, size=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>:
...         <span style="color: black;">iterable</span> = <span style="color: #008000;">iter</span><span style="color: black;">&#40;</span>iterable<span style="color: black;">&#41;</span>
...         <span style="color: black;">d</span> = deque<span style="color: black;">&#40;</span>islice<span style="color: black;">&#40;</span>iterable, size<span style="color: black;">&#41;</span>, size<span style="color: black;">&#41;</span>
...         <span style="color: #ff7700;font-weight:bold;">yield</span> d
...         <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> iterable:
...                 <span style="color: black;">d</span>.<span style="color: black;">append</span><span style="color: black;">&#40;</span>x<span style="color: black;">&#41;</span>
...                 <span style="color: #ff7700;font-weight:bold;">yield</span> d
...         
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> window<span style="color: black;">&#40;</span><span style="color: #483d8b;">'azertyuiop'</span><span style="color: black;">&#41;</span>:
...         <span style="color: #ff7700;font-weight:bold;">print</span> x
...     
<span style="color: black;">deque</span><span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #483d8b;">'a'</span>, <span style="color: #483d8b;">'z'</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #483d8b;">'z'</span>, <span style="color: #483d8b;">'e'</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #483d8b;">'e'</span>, <span style="color: #483d8b;">'r'</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #483d8b;">'r'</span>, <span style="color: #483d8b;">'t'</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #483d8b;">'t'</span>, <span style="color: #483d8b;">'y'</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #483d8b;">'y'</span>, <span style="color: #483d8b;">'u'</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #483d8b;">'u'</span>, <span style="color: #483d8b;">'i'</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #483d8b;">'i'</span>, <span style="color: #483d8b;">'o'</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
deque<span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #483d8b;">'o'</span>, <span style="color: #483d8b;">'p'</span><span style="color: black;">&#93;</span>, maxlen=<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Vous noterez au passage que nous faisons ici un usage malin des <a href="http://sametmax.com/comment-utiliser-yield-et-les-generateurs-en-python/">générateurs</a>, ce qui nous permet de retourner un itérable sans tout charger en mémoire et de slider sur notre window avec classe.</p>
<p>Ainsi on peut se la peter en faisant des trucs compliqués en une ligne comme:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: black;">&#123;</span><span style="color: #008000;">tuple</span><span style="color: black;">&#40;</span>d<span style="color: black;">&#41;</span>: i <span style="color: #ff7700;font-weight:bold;">for</span> i, d <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">enumerate</span><span style="color: black;">&#40;</span>window<span style="color: black;">&#40;</span><span style="color: #008000;">xrange</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">10</span><span style="color: black;">&#41;</span>, <span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span><span style="color: black;">&#125;</span>
<span style="color: black;">&#123;</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">5</span>, <span style="color: #ff4500;">6</span>, <span style="color: #ff4500;">7</span><span style="color: black;">&#41;</span>: <span style="color: #ff4500;">5</span>, <span style="color: black;">&#40;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>: <span style="color: #ff4500;">0</span>, <span style="color: black;">&#40;</span><span style="color: #ff4500;">7</span>, <span style="color: #ff4500;">8</span>, <span style="color: #ff4500;">9</span><span style="color: black;">&#41;</span>: <span style="color: #ff4500;">7</span>, <span style="color: black;">&#40;</span><span style="color: #ff4500;">6</span>, <span style="color: #ff4500;">7</span>, <span style="color: #ff4500;">8</span><span style="color: black;">&#41;</span>: <span style="color: #ff4500;">6</span>, <span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span>: <span style="color: #ff4500;">1</span>, <span style="color: black;">&#40;</span><span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span><span style="color: black;">&#41;</span>: <span style="color: #ff4500;">3</span>, <span style="color: black;">&#40;</span><span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span><span style="color: black;">&#41;</span>: <span style="color: #ff4500;">2</span>, <span style="color: black;">&#40;</span><span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span>, <span style="color: #ff4500;">6</span><span style="color: black;">&#41;</span>: <span style="color: #ff4500;">4</span><span style="color: black;">&#125;</span></pre></div></div>

<p>Ce qui n&#8217;a absolument aucun intérêt, mais si vous comprenez ce que ça fait, alors vous avec bien masterisé Python.</p>


feed_id: http://sametmax.com/?p=3813
title: Heapq, le module Python incompris
uri: Heapq-le-module-Python-incompris
url: http://sametmax.com/heapq-le-module-python-incompris/
content:
<p>Guido Van Rossum, notre-Dieu-à-tous-beni-soit-il, a un jour accepté de faire une session de questions-réponses publique, dans laquelle un petit malin lui a demandé &#8220;<a href="http://neopythonic.blogspot.fr/2008/10/sorting-million-32-bit-integers-in-2mb.html">Comment ordonner un million d&#8217;entiers 32 bits dans 2Mo de Ram avec Python</a>&#8220;.</p>
<p>Ca aurait été sur ce blog, le mec se serait pris un tampon &#8220;drozophiliafucker&#8221; dans la gueule et ça aurait été plié. Mais quand on est BDFL et, à l&#8217;époque, employé chez Google, on est obligé de donner une réponse un peu sérieuse.</p>
<p>Si vous avez suivi le lien précédent, vous verrez que sa réponse implique un obscure module appelé heapq. Si vous allez sur <a href="http://docs.python.org/2/library/heapq.html">la doc</a> du-dit module, vous verrez qu&#8217;elle implique une obscure explication innomable et vous aller retourner à la vidéo de porn que vous avez laissé bufferiser en haute résolution afin de pouvoir voir les grains de beauté qui longent le pourtour anal de la principale protagoniste. Respirons. </p>
<h2>Il y a une explication rationnelle à tout cela</h2>
<p>heapq est un algorithme qui organise une liste sous forme d&#8217;arbre binaire. Vous voyez c&#8217;était simple non ?</p>
<p>Nan je déconne, je vais pas vous laisser avec ça quand même.</p>
<p>Le module heapq permet d&#8217;utiliser le type &#8220;list&#8221; pour y ajouter ou retirer les éléments de telle sorte qu&#8217;ils soient toujours dans l&#8217;ordre.</p>
<p>Sous le capot, ça marche effectivement avec un arbre binaire, mais on s&#8217;en branle. Tout ce qu&#8217;il faut comprendre c&#8217;est:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">heapq</span> <span style="color: #ff7700;font-weight:bold;">import</span> heappush
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l = <span style="color: black;">&#91;</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> heappush<span style="color: black;">&#40;</span>l, <span style="color: #ff4500;">69</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> heappush<span style="color: black;">&#40;</span>l, <span style="color: #ff4500;">42</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> heappush<span style="color: black;">&#40;</span>l, <span style="color: #ff4500;">2048</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> heappush<span style="color: black;">&#40;</span>l, -<span style="color: #ff4500;">273.15</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l <span style="color: #808080; font-style: italic;"># la liste est ordonnée en arbre binaire...</span>
<span style="color: black;">&#91;</span>-<span style="color: #ff4500;">273.15</span>, <span style="color: #ff4500;">42</span>, <span style="color: #ff4500;">2048</span>, <span style="color: #ff4500;">69</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">xrange</span><span style="color: black;">&#40;</span><span style="color: #008000;">len</span><span style="color: black;">&#40;</span>l<span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>: <span style="color: #808080; font-style: italic;"># et on depop pour itérer dans l'odre</span>
    <span style="color: #ff7700;font-weight:bold;">print</span> heappop<span style="color: black;">&#40;</span>l<span style="color: black;">&#41;</span>
...     
-<span style="color: #ff4500;">273.15</span>
<span style="color: #ff4500;">42</span>
<span style="color: #ff4500;">69</span>
<span style="color: #ff4500;">2048</span></pre></div></div>

<p>Donc on a une liste, on lui met des éléments dans la tronche dans n&#8217;importe quel ordre, et bam, on peut itérer dans le bon ordre sans avoir à rien faire. Et cette insertion est assez rapide (O(lg n) pour les tatillons). Le parcours l&#8217;est également (de l&#8217;ordre de O(n log n)).</p>
<p>Et donc c&#8217;est très pratique pour trouver les x plus petits éléments (ou les plus grands), implémenter des queues de priorité, etc.</p>
<p>Exemple de queue de priorité, (courageusement <a href="http://joernhees.de/blog/2010/07/19/min-heap-in-python/">volé d&#8217;ici</a>):</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">heapq</span>
&nbsp;
<span style="color: #ff7700;font-weight:bold;">class</span> PriorityQueue<span style="color: black;">&#40;</span><span style="color: #008000;">list</span><span style="color: black;">&#41;</span>:
&nbsp;
    <span style="color: #ff7700;font-weight:bold;">def</span> <span style="color: #0000cd;">__init__</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span>, data<span style="color: black;">&#41;</span>:
        <span style="color: #008000;">super</span><span style="color: black;">&#40;</span>Heap, <span style="color: #008000;">self</span><span style="color: black;">&#41;</span>.<span style="color: #0000cd;">__init__</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
        <span style="color: #ff7700;font-weight:bold;">for</span> i, x <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">enumerate</span><span style="color: black;">&#40;</span>data<span style="color: black;">&#41;</span>:
            <span style="color: #008000;">self</span>.<span style="color: black;">push</span><span style="color: black;">&#40;</span>i, x<span style="color: black;">&#41;</span>
&nbsp;
    <span style="color: #ff7700;font-weight:bold;">def</span> push<span style="color: black;">&#40;</span><span style="color: #008000;">self</span>, priority, item<span style="color: black;">&#41;</span>:
        <span style="color: #483d8b;">&quot;&quot;&quot;
            On push en rajoute une priorité
        &quot;&quot;&quot;</span>
        <span style="color: #dc143c;">heapq</span>.<span style="color: black;">heappush</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span>, <span style="color: black;">&#40;</span>priority, item<span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>
&nbsp;
    <span style="color: #ff7700;font-weight:bold;">def</span> pop<span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>:
        <span style="color: #483d8b;">&quot;&quot;&quot;
            On pop en retirant la proprité
        &quot;&quot;&quot;</span>
        <span style="color: #ff7700;font-weight:bold;">return</span> <span style="color: #dc143c;">heapq</span>.<span style="color: black;">heappop</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">1</span><span style="color: black;">&#93;</span>
&nbsp;
    <span style="color: #ff7700;font-weight:bold;">def</span> <span style="color: #0000cd;">__len__</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>:
        <span style="color: #ff7700;font-weight:bold;">return</span> <span style="color: #008000;">len</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>
&nbsp;
    <span style="color: #ff7700;font-weight:bold;">def</span> <span style="color: #0000cd;">__iter__</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>:
        <span style="color: #483d8b;">&quot;&quot;&quot;
            Comme on a une méthode next(), on peut se retourner soi-même.
            Ainsi la boucle for appelera next() automatiquement. 
        &quot;&quot;&quot;</span>
        <span style="color: #ff7700;font-weight:bold;">return</span> <span style="color: #008000;">self</span>
&nbsp;
    <span style="color: #ff7700;font-weight:bold;">def</span> next<span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>:
        <span style="color: #483d8b;">&quot;&quot;&quot; 
           On depop la liste du plus petit au plus grand.
        &quot;&quot;&quot;</span>
        <span style="color: #ff7700;font-weight:bold;">try</span>:
            <span style="color: #ff7700;font-weight:bold;">return</span> <span style="color: #008000;">self</span>.<span style="color: black;">pop</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
        <span style="color: #ff7700;font-weight:bold;">except</span> <span style="color: #008000;">IndexError</span>:
            <span style="color: #ff7700;font-weight:bold;">raise</span> <span style="color: #008000;">StopIteration</span>
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l = PriorityQueue<span style="color: black;">&#40;</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;azerty&quot;</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l.<span style="color: black;">push</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">100</span>, <span style="color: #483d8b;">'après'</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l.<span style="color: black;">push</span><span style="color: black;">&#40;</span>-<span style="color: #ff4500;">1</span>, <span style="color: #483d8b;">'avant'</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l.<span style="color: black;">push</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">5</span>, <span style="color: #483d8b;">'pendant'</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> l:
...     <span style="color: #ff7700;font-weight:bold;">print</span> x
...     
<span style="color: black;">avant</span>
a
z
e
r
t
pendant
y
après</pre></div></div>

<p>Et le plus beau, c&#8217;est qu&#8217;on peut prendre plusieurs itérables ordonnés, et utiliser <code>heapq.merge</code> pour obtenir un générateur (qui ne charge pas tout en mémoire d&#8217;un coup) qui va permettre d&#8217;iterer de manière ordonnée sur tous les éléments.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">heapq</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l1 = <span style="color: #008000;">sorted</span><span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #dc143c;">random</span>.<span style="color: black;">randint</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1000</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">xrange</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">5</span><span style="color: black;">&#41;</span><span style="color: black;">&#93;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l2 = <span style="color: #008000;">sorted</span><span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #dc143c;">random</span>.<span style="color: black;">randint</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1000</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">xrange</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">5</span><span style="color: black;">&#41;</span><span style="color: black;">&#93;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l3 = <span style="color: #008000;">sorted</span><span style="color: black;">&#40;</span><span style="color: black;">&#91;</span><span style="color: #dc143c;">random</span>.<span style="color: black;">randint</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1000</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">xrange</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">5</span><span style="color: black;">&#41;</span><span style="color: black;">&#93;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">list</span><span style="color: black;">&#40;</span><span style="color: #dc143c;">heapq</span>.<span style="color: black;">merge</span><span style="color: black;">&#40;</span>l1, l2, l3<span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">52</span>, <span style="color: #ff4500;">59</span>, <span style="color: #ff4500;">60</span>, <span style="color: #ff4500;">171</span>, <span style="color: #ff4500;">174</span>, <span style="color: #ff4500;">262</span>, <span style="color: #ff4500;">336</span>, <span style="color: #ff4500;">402</span>, <span style="color: #ff4500;">435</span>, <span style="color: #ff4500;">487</span>, <span style="color: #ff4500;">557</span>, <span style="color: #ff4500;">645</span>, <span style="color: #ff4500;">899</span>, <span style="color: #ff4500;">949</span>, <span style="color: #ff4500;">996</span><span style="color: black;">&#93;</span></pre></div></div>

<p>Notez que ce n&#8217;est pas du tout la même chose que de concaténer les listes:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> l1 + l2 + l3
<span style="color: black;">&#91;</span><span style="color: #ff4500;">59</span>, <span style="color: #ff4500;">174</span>, <span style="color: #ff4500;">336</span>, <span style="color: #ff4500;">487</span>, <span style="color: #ff4500;">996</span>, <span style="color: #ff4500;">52</span>, <span style="color: #ff4500;">171</span>, <span style="color: #ff4500;">557</span>, <span style="color: #ff4500;">645</span>, <span style="color: #ff4500;">949</span>, <span style="color: #ff4500;">60</span>, <span style="color: #ff4500;">262</span>, <span style="color: #ff4500;">402</span>, <span style="color: #ff4500;">435</span>, <span style="color: #ff4500;">899</span><span style="color: black;">&#93;</span></pre></div></div>

<p>Car des élements de <code>l2</code> peuvent être inférieurs à ceux de <code>l1</code>. <code>heap.merge</code> nous ordonne tout bien correctement. C&#8217;est l&#8217;équivalent de <code>sorted(l1 + l2 + l3)</code>, sauf que ça ne charge pas tout en mémoire:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">heapq</span>.<span style="color: black;">merge</span><span style="color: black;">&#40;</span>l1, l2, l3<span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>generator <span style="color: #008000;">object</span> merge at 0x0314F238<span style="color: #66cc66;">&gt;</span></pre></div></div>

<p>Alors que <code>sorted()</code>, charge tout en mémoire:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">sorted</span><span style="color: black;">&#40;</span>l1 + l2 + l3<span style="color: black;">&#41;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">52</span>, <span style="color: #ff4500;">59</span>, <span style="color: #ff4500;">60</span>, <span style="color: #ff4500;">171</span>, <span style="color: #ff4500;">174</span>, <span style="color: #ff4500;">262</span>, <span style="color: #ff4500;">336</span>, <span style="color: #ff4500;">402</span>, <span style="color: #ff4500;">435</span>, <span style="color: #ff4500;">487</span>, <span style="color: #ff4500;">557</span>, <span style="color: #ff4500;">645</span>, <span style="color: #ff4500;">899</span>, <span style="color: #ff4500;">949</span>, <span style="color: #ff4500;">996</span><span style="color: black;">&#93;</span></pre></div></div>

<p><del datetime="2012-12-21T17:35:16+00:00">Bien entendu, ça marche avec des listes créées avec </del><br />
<del datetime="2012-12-21T17:35:16+00:00"><code>heapq</code>, ainsi:</del></p>
<p><del datetime="2012-12-21T17:35:16+00:00">>>> l1 = []</del></p>
<p><del datetime="2012-12-21T17:35:16+00:00">>>> for x in xrange(5): heappush(l1, random.randint(0, 1000))</del></p>
<p><del datetime="2012-12-21T17:35:16+00:00">>>> l2 = []</del></p>
<p><del datetime="2012-12-21T17:35:16+00:00">>>> for x in xrange(5): heappush(l2, random.randint(0, 1000))</del></p>
<p><del datetime="2012-12-21T17:35:16+00:00">>>> l3 = []</del></p>
<p><del datetime="2012-12-21T17:35:16+00:00">>>> for x in xrange(5): heappush(l3, random.randint(0, 1000))</del></p>
<p><del datetime="2012-12-21T17:35:16+00:00">>>> list(heapq.merge(l1, l2, l3))</del></p>
<p><del datetime="2012-12-21T17:35:16+00:00">[31, 40, 133, 360, 504, 508, 513, 679, 645, 792, 838, 413, 765, 886, 924]</del></p>
<p><em>(Grosse connasserie de ma part, faites comme si vous aviez rien vu.)</em></p>
<p>Quand on a de grosses quantités de données à trier, c&#8217;est très pratique, car l&#8217;effort de tri est répartie à chaque insertion, et à chaque itération pendant le parcours, pas concentré sur de gros appels de <code>sorted()</code>.</p>
<p>On peut aussi récupérer des trucs du genre, les n plus petits / grands éléments sans tout coder à la main:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> l = <span style="color: black;">&#91;</span><span style="color: #dc143c;">random</span>.<span style="color: black;">randint</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1000</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">xrange</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">100</span><span style="color: black;">&#41;</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">heapq</span>.<span style="color: black;">nsmallest</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">4</span>, l<span style="color: black;">&#41;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">7</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">heapq</span>.<span style="color: black;">nlargest</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">3</span>, l<span style="color: black;">&#41;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">999</span>, <span style="color: #ff4500;">996</span>, <span style="color: #ff4500;">983</span><span style="color: black;">&#93;</span></pre></div></div>

<p>Et c&#8217;est beaucoup plus efficace que de le faire soi-même.</p>
<p>J&#8217;en profite pour rappeler au passage que tous les objets en Python sont ordonnables:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span> <span style="color: #66cc66;">&gt;</span> <span style="color: black;">&#40;</span><span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: #008000;">False</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span> <span style="color: #66cc66;">&lt;</span> <span style="color: black;">&#40;</span><span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: #008000;">True</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #483d8b;">&quot;a&quot;</span> <span style="color: #66cc66;">&gt;</span> <span style="color: #483d8b;">&quot;b&quot;</span>
<span style="color: #008000;">False</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #483d8b;">&quot;a&quot;</span> <span style="color: #66cc66;">&lt;</span> <span style="color: #483d8b;">&quot;b&quot;</span>
<span style="color: #008000;">True</span></pre></div></div>

<p>Et qu&#8217;en définissant les méthodes <a href="http://docs.python.org/2/reference/datamodel.html#object.__eq__">__eq_</a>_, <code>__lt__</code>, <code>__gt__</code>, etc., on peut donner un moyen de <a href="http://wiki.python.org/moin/HowTo/Sorting">comparer n&#8217;importe quelle classe</a>.</p>
<p>Bref, pour tous les besoins de classement, de priorisations, d&#8217;ordonnancement, de notion de plus petits, de plus grands, etc. qui concernent un gros jeu de données, <code>heapq</code> est le module qu&#8217;il vous faut.</p>
<p>Et là je percute que ça fait quelque temps déjà que je fais des articles élitistes pour des uses cases de 1% de la population. Donc les prochains tutos concerneront des trucs plus terre à terre. Parce que, je fais le malin là, mais je savais pas à quoi servait <code>heapq</code> il y a 3 semaines.</p>
<p>xoxo les filles</p>


feed_id: http://sametmax.com/?p=3827
title: Quel hébergement Web pour les projets Python ?
uri: Quel-hébergement-Web-pour-les-projets-Python
url: http://sametmax.com/quel-hebergement-web-pour-les-projets-python/
content:
<p>Un lecteur m&#8217;a demandé il y a quelques temps quel hébergement choisir pour son projet Django, en ces termes poétiques:</p>
<blockquote><p>Chez moi, je teste un peu les frameworks web python django et pyramid. Seulement une question demeure à laquelle je ne trouve pas de réponse probante : OK j&#8217;ai fait mon super site en python OK il demoule sur mon pc perso Mais maintenant, quel hébergeur utiliser ?</p></blockquote>
<p>D&#8217;abord, je vous invite à consulter les listes des hébergeurs <a href="http://wiki.python.org/moin/FreeHosts">gratuits</a> et <a href="http://wiki.python.org/moin/SpecializedCommercialHosts">payants</a> sur le wiki officiel de Python.</p>
<p>Parmi les hosts gratuits, j&#8217;ai essayé et approuvé <a href="http://www.pythonanywhere.com">PythonAnywhere</a> qui est parfait pour un petit projet. Il gère très bien WSGI donc on peut facilement y plugger Django, Bottle, ou Flask. Et pas besoin de savoir comment configurer un serveur, il y a juste quelques réglages et roulez jeunesse.</p>
<p>De réputation, il y a aussi <a href="https://www.alwaysdata.com/">AlwaysData</a> en hosting gratuit. Certes je ne l&#8217;ai pas essayé, mais il est sponsor de pas mal d&#8217;événements Python et rien que pour ça, ça me donne envie de le soutenir. Par contre avec 10 Mo de disque, vous avez intérêt à pas viser trop gros.</p>
<p>Dans la liste des hébergeurs gratuits, il n&#8217;est pas fait mention de <a href="https://developers.google.com/appengine/">Google App Engine</a>. Pourtant l&#8217;offre de base est bien gratuite, même si si ça devient payant assez vite. Il faut aussi savoir que ce n&#8217;est pas une installation Python standard, et qu&#8217;il n&#8217;y a pas de base de données autre que l&#8217;API Big Data de Google. Bref, c&#8217;est assez particulier.</p>
<p>Néanmoins, une fois que votre projet dépote, un hébergeur gratuit ne suffit plus. Dans un premier temps, vous pouvez vous lancer dans un hébergeur pas cher, mais sur un serveur dédié. Ca demande un peu de sysadmin, mais vous êtes plus libres.</p>
<p><a href="http://www.online.net/fr">Online.net</a> et sa fameuse offre Dedibox est probablement un des meilleurs rapport qualité / prix puisque vous aurez un serveur dédié pour 9 euros / mois. C&#8217;est quand même pas la mer à boire de débourser 10 balles, et on est tranquille. Ce n&#8217;est pas un hasard, c&#8217;est une filiale d&#8217;Iliad qui n&#8217;est autre que la maison mère de Free. C&#8217;est une super opportunité pour se faire la main, car on s&#8217;en branle un peu de tuer un serveur à 10 euros, donc on peut s&#8217;amuser avec, apprendre à config redis, optimiser PosGres, faire un proxy VPN ou un spam bot via Tor. Très chouette.</p>
<p>Alternativement, vous pouvez faire confiance au français <a href="https://www.gandi.net/">Gandi</a>. C&#8217;est un poil plus cher, mais leur service est excellent, et c&#8217;est une boîte qui a une très belle éthique. Vous aurez alors un serveur dédié, mais virtualisé, donc vous pourrez augmenter la puissance a posteriori alors qu&#8217;avec la dédiboule, vous êtes bon pour migrer tout le serveur.</p>
<p>Après, il faut carrément taper dans les services près des back bones si on veut monter dans les tours. En ce moment, on aime pas mal <a href="http://www.leaseweb.com/">Leaseweb</a>. Là on aligne deux zéros mensuels par serveurs sur la facture, mais c&#8217;est déjà des jolis bébés.</p>
<p>Pour finir, vous voudrez peut-être passer en mode Cloud, et dans ce cas <a href="https://www.rackspace.com/">Rackspace</a> et <a href="http://www.webfaction.com/">WebFaction</a> ont une très bonne réputation, particulièrement en terme de support. Leur facture est par contre salée, mais le nuage, c&#8217;est toujours cher au kilo.</p>
<p>Si vous êtes du genre à aimer les trucs fashions et bien intégré,<a href="http://www.heroku.com/"> Heroku</a> et <a href="https://gondor.io/">Gondor</a> ont des solutions spécialisées autour de Python. Tout ce qui est déploiement se fait apparemment les doigts dans le pif si vous êtes du genre à pas aimer le sysadmin, avec intégration du versioning et des migrations. Bref, le truc hype de la vibes du flex. Enfin c&#8217;est ce qu&#8217;on dit, car on a pas testé. On aime avoir le contrôle sur nos machines.</p>
<p>Enfin, mention spéciale à <a href="http://www.cinfu.com/">Cinfu</a> qui propose des serveurs payables en <a href="http://sametmax.com/quest-ce-que-bitcoin/">Bitcoin</a>. Toujours utile pour créer un site de phishing. Ils interdisent les nœuds Tor par contre.</p>


feed_id: http://sametmax.com/?p=3644
title: Quelques bonnes raisons de plus d’utiliser iPython
uri: Quelques-bonnes-raisons-de-plus-d-utiliser-iPython
url: http://sametmax.com/quelques-bonnes-raisons-de-plus-dutiliser-ipython/
content:
<p>Le shell Python est vraiment pratique pour expérimenter, apprendre le langage, tester un snippet vitos ou administrer son site à distance. Mais <a href="http://ipython.org/">iPython</a>, ola, iPython, il déchire sa génitrice avec une poutrelle en verre pilé.</p>
<p>Voici quelques commandes qui vous donneront moult raisons de plus pour très vite installer ce shell alternatif.</p>
<h2>Autocall</h2>
<p>Taper des parenthèses et des guillemets, c&#8217;est sooooooo 1995.  iPython peut vous les rajouter automatiquement dans les appels de fonctions, il faut juste préfixer de &#8220;/&#8221;, &#8220;,&#8221; ou &#8220;;&#8221; votre appel de fonction pour qu&#8217;il fasse la conversion:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">/f <span style="color: #ff4500;">1</span>,<span style="color: #ff4500;">2</span> =<span style="color: #66cc66;">&gt;</span> f<span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>,<span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
,f <span style="color: #ff4500;">1</span> <span style="color: #ff4500;">2</span> =<span style="color: #66cc66;">&gt;</span> f<span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;1&quot;</span>,<span style="color: #483d8b;">&quot;2&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">;</span>f <span style="color: #ff4500;">1</span> <span style="color: #ff4500;">2</span> =<span style="color: #66cc66;">&gt;</span> f<span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;1 2&quot;</span><span style="color: black;">&#41;</span></pre></div></div>

<h2>Accès au shell système</h2>
<p>Préfixez votre commande d&#8217;un &#8220;!&#8221; bien couillu, et iPython va vous exécuter ça dans le shell système (par exemple bash) et vous retourner le résulat:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #66cc66;">!</span> cat /etc/fstab | grep <span style="color: #483d8b;">'ext4'</span>
UUID=e33c5b98-<span style="color: #ff4500;">1570</span>-44d6-a32f-5e7970e1e588 /               ext4    errors=remount-ro <span style="color: #ff4500;">0</span>       <span style="color: #ff4500;">1</span></pre></div></div>

<p>Oui, oui, on est dans un shell Python là. Ou comment bien faire chier la coloration syntaxique de votre blog.</p>
<p>Et on peut mettre tout ça dans une variable et le traiter en Python derrière:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> files = <span style="color: #66cc66;">!</span>ls
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: black;">&#91;</span>f.<span style="color: black;">upper</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">for</span> f <span style="color: #ff7700;font-weight:bold;">in</span> files<span style="color: black;">&#93;</span>
<span style="color: black;">&#91;</span><span style="color: #483d8b;">'BUREAU'</span>, <span style="color: #483d8b;">'DOCUMENTS'</span>, <span style="color: #483d8b;">'EXAMPLES.DESKTOP'</span>, <span style="color: #483d8b;">'IMAGES'</span>, <span style="color: #483d8b;">'MOD<span style="color: #000099; font-weight: bold;">\x</span>c3<span style="color: #000099; font-weight: bold;">\x</span>a8LES'</span>, <span style="color: #483d8b;">'MUSIQUE'</span>, <span style="color: #483d8b;">'PUBLIC'</span>, <span style="color: #483d8b;">'T<span style="color: #000099; font-weight: bold;">\x</span>c3<span style="color: #000099; font-weight: bold;">\x</span>a9L<span style="color: #000099; font-weight: bold;">\x</span>c3<span style="color: #000099; font-weight: bold;">\x</span>a9CHARGEMENTS'</span>, <span style="color: #483d8b;">'UBUNTU ONE'</span>, <span style="color: #483d8b;">'VID<span style="color: #000099; font-weight: bold;">\x</span>c3<span style="color: #000099; font-weight: bold;">\x</span>a9OS'</span>,<span style="color: black;">&#93;</span></pre></div></div>

<p>A noter que tout est exécuté dans un autre process, ainsi <code>!cd</code> n&#8217;aura aucun effet. Mais tout est prévu: <code>%cd</code> et <code>%pwd</code> proxient tout ça vers <code>os.chdir</code> et <code>os.getcwd</code> :-)</p>
<h2>Debugger</h2>
<p>Entrez <code>%timeit</code> expression pour qu&#8217;il qu&#8217;iPython vous l&#8217;exécute 10000000 fois et vous donne sa performance.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #66cc66;">%</span><span style="color: #dc143c;">timeit</span> x=<span style="color: #ff4500;">2</span><span style="color: #66cc66;">**</span><span style="color: #ff4500;">100</span>
<span style="color: #ff4500;">10000000</span> loops, best of <span style="color: #ff4500;">3</span>: <span style="color: #ff4500;">22.5</span> ns per loop</pre></div></div>

<p>Autre commande: <code>%pdb</code> vous lancera automatiquement votre <a href="http://sametmax.com/debugger-en-python-les-bases-de-pdb/">débuggeur favoris</a> si une exception se lève durant votre session.</p>
<h2>Se faciliter la vie</h2>
<p><code>%edit</code> ouvre un editeur (par défault VI sous nunux, mais c&#8217;est <a href="http://sametmax.com/personnalisez-le-demarrage-dipython/">configurable</a>), et si vous sauvegardez, le contenu tapé est récupéré et exécuté par iPython. Génial pour les bouts de code trop relou à taper sur le prompt.</p>
<p><code>%gui qt|wx|gtk</code> lance l&#8217;intégration de la main loop d&#8217;un des toolkits graphiques afin pour de pouvoir faire mumuse avec des widgets sans bloquer votre shell.</p>
<p>Vous étiez vous demandé pourquoi le prompt iPython était plein de <code>In</code> et de <code>Out</code>, et pas de <code>>>></code> ? Parce que tout l&#8217;historique est numéroté, et accessible:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">In <span style="color: black;">&#91;</span><span style="color: #ff4500;">38</span><span style="color: black;">&#93;</span>: <span style="color: #ff4500;">1</span> + <span style="color: #ff4500;">1</span>
Out<span style="color: black;">&#91;</span><span style="color: #ff4500;">38</span><span style="color: black;">&#93;</span>: <span style="color: #ff4500;">2</span>
&nbsp;
In <span style="color: black;">&#91;</span><span style="color: #ff4500;">39</span><span style="color: black;">&#93;</span>: In<span style="color: black;">&#91;</span><span style="color: #ff4500;">38</span><span style="color: black;">&#93;</span>
Out<span style="color: black;">&#91;</span><span style="color: #ff4500;">39</span><span style="color: black;">&#93;</span>: u<span style="color: #483d8b;">'1 + 1'</span>
&nbsp;
In <span style="color: black;">&#91;</span><span style="color: #ff4500;">40</span><span style="color: black;">&#93;</span>: Out<span style="color: black;">&#91;</span><span style="color: #ff4500;">38</span><span style="color: black;">&#93;</span>
Out<span style="color: black;">&#91;</span><span style="color: #ff4500;">40</span><span style="color: black;">&#93;</span>: <span style="color: #ff4500;">2</span></pre></div></div>

<p>Mais vous pouvez aussi utiliser <code>%doctest_mode</code> qui donne à votre prompt un air de shell Python normal. L&#8217;avantage ? On peut copier le contenu d&#8217;un autre shell dedans (et donc d&#8217;une doctest) avec les chevrons !</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">In <span style="color: black;">&#91;</span><span style="color: #ff4500;">49</span><span style="color: black;">&#93;</span>: <span style="color: #66cc66;">%</span>doctest_mode
<span style="color: #008000;">Exception</span> reporting mode: Plain
Doctest mode <span style="color: #ff7700;font-weight:bold;">is</span>: ON
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">for</span> pom <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: black;">&#40;</span><span style="color: #483d8b;">'pom'</span>, <span style="color: #483d8b;">'pom'</span>, <span style="color: #483d8b;">'pom'</span>, <span style="color: #483d8b;">'pom'</span><span style="color: black;">&#41;</span>:
...     ...     <span style="color: #ff7700;font-weight:bold;">print</span> pom
...     ... 
<span style="color: black;">pom</span>
pom
pom
pom</pre></div></div>


feed_id: http://sametmax.com/?p=3851
title: Les nombres en Python
uri: Les-nombres-en-Python
url: http://sametmax.com/les-nombres-en-python/
content:
<p>Aller, un petit article pour débutant pour changer: la représentation des nombres en Python.</p>
<h2>Les types de base</h2>
<p>Il y a plus de types et notations numériques de base que vous ne le pensez:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>type <span style="color: #483d8b;">'int'</span><span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1.0</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>type <span style="color: #483d8b;">'float'</span><span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">11111111111111111111</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>type <span style="color: #483d8b;">'long'</span><span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span>1j<span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>type <span style="color: #483d8b;">'complex'</span><span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span>1e10<span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>type <span style="color: #483d8b;">'float'</span><span style="color: #66cc66;">&gt;</span></pre></div></div>

<p><code>1</code> est celui que tout le monde connaît le mieux. Il représente le type entier, c&#8217;est à dire sans virgule. C&#8217;est aussi celui qu&#8217;on utilise le plus puisqu&#8217;il sert aux indices, aux slicings, aux boucles, au compteurs, etc.</p>
<p>Il peut être négatif:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> -<span style="color: #ff4500;">2</span> + <span style="color: #ff4500;">1</span>
-<span style="color: #ff4500;">1</span></pre></div></div>

<p>Et permet la plupart des opérations mathématiques ordinaires:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">1</span> + <span style="color: #ff4500;">1</span> <span style="color: #808080; font-style: italic;"># addition</span>
<span style="color: #ff4500;">2</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">1</span> - <span style="color: #ff4500;">1</span> <span style="color: #808080; font-style: italic;"># soustraction</span>
<span style="color: #ff4500;">0</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">4</span> / <span style="color: #ff4500;">2</span> <span style="color: #808080; font-style: italic;"># division</span>
<span style="color: #ff4500;">2</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">2</span> <span style="color: #66cc66;">*</span> <span style="color: #ff4500;">3</span> <span style="color: #808080; font-style: italic;"># multiplication</span>
<span style="color: #ff4500;">6</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">2</span> <span style="color: #66cc66;">**</span> <span style="color: #ff4500;">3</span> <span style="color: #808080; font-style: italic;"># puissance</span>
<span style="color: #ff4500;">8</span></pre></div></div>

<p>Ça va sans dire, mais ça va mieux en le disant, Python n&#8217;applique pas de transtypage automatique en dehors des types numériques. Comme disait ma maîtresse, on ne peut pas additionner des choux et des carottes, ni des <code>strings</code> et des <del>bas nylons</del> <code>int</code>:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">1</span> + <span style="color: #ff4500;">1</span>
<span style="color: #ff4500;">2</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">1</span> + <span style="color: #483d8b;">&quot;1&quot;</span>
Traceback <span style="color: black;">&#40;</span>most recent call last<span style="color: black;">&#41;</span>:
  File <span style="color: #483d8b;">&quot;&lt;ipython-input-132-db0423a23ce2&gt;&quot;</span>, line <span style="color: #ff4500;">1</span>, <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #66cc66;">&lt;</span>module<span style="color: #66cc66;">&gt;</span>
    <span style="color: #ff4500;">1</span> + <span style="color: #483d8b;">&quot;1&quot;</span>
<span style="color: #008000;">TypeError</span>: unsupported operand <span style="color: #008000;">type</span><span style="color: black;">&#40;</span>s<span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">for</span> +: <span style="color: #483d8b;">'int'</span> <span style="color: #ff7700;font-weight:bold;">and</span> <span style="color: #483d8b;">'str'</span>
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">1</span> + <span style="color: #008000;">int</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;1&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #ff4500;">2</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">str</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span> + <span style="color: #483d8b;">&quot;1&quot;</span>
<span style="color: #483d8b;">'11'</span></pre></div></div>

<p>Quand un entier est trop gros, il est transformé automatiquement en type <code>long</code>. Il n&#8217;y a rien à faire, Python gère ça tout seul. Un long, c&#8217;est juste un gros entier, un peu plus lent.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">sys</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">sys</span>.<span style="color: black;">maxint</span> <span style="color: #808080; font-style: italic;"># la limite de transformation d'un int en long</span>
<span style="color: #ff4500;">9223372036854775807</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">9223372036854775807</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>type <span style="color: #483d8b;">'int'</span><span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">9223372036854775807</span> + <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>type <span style="color: #483d8b;">'long'</span><span style="color: #66cc66;">&gt;</span></pre></div></div>

<p>Mais on peut en faire un soi-même si on se sent l&#8217;âme d&#8217;un créateur de <code>long</code>, même un tout petit. Il suffit de rajouter un <em>L</em>:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> 1L
1L
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span>1L<span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>type <span style="color: #483d8b;">'long'</span><span style="color: #66cc66;">&gt;</span></pre></div></div>

<p>Ce type n&#8217;existe plus en Python 3.</p>
<p>Les <code>int</code> et <code>long</code> sont limités à ce qui est entier. Pour tout ce qui a une virgule, on utilise les flottants, qui accepte les mêmes opérations:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">0.1</span> - <span style="color: #ff4500;">2.3</span> <span style="color: #66cc66;">*</span> <span style="color: #ff4500;">4.5</span> <span style="color: #66cc66;">**</span> <span style="color: #ff4500;">6.7</span> / <span style="color: #ff4500;">8.9</span>
-<span style="color: #ff4500;">6149.7096223012195</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">type</span><span style="color: black;">&#40;</span>-<span style="color: #ff4500;">6149.7096223012195</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&lt;</span>type <span style="color: #483d8b;">'float'</span><span style="color: #66cc66;">&gt;</span></pre></div></div>

<p>Tout nombre qui contient un <code>.</code> est automatiquement un <code>float</code>.</p>
<p>D&#8217;ailleurs, si on fait une opération entre un <code>int</code> et un <code>float</code>, on se retrouve avec un résultat en flottant:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">1</span> + <span style="color: #ff4500;">1</span>. <span style="color: #808080; font-style: italic;"># même pas besoin de chiffre après la virgule</span>
<span style="color: #ff4500;">2.0</span></pre></div></div>

<p>En fait, la plupart des opérations mathématiques un peu avancées retournent un <code>float</code>:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">math</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">math</span>.<span style="color: black;">cos</span><span style="color: black;">&#40;</span><span style="color: #dc143c;">math</span>.<span style="color: black;">pi</span><span style="color: black;">&#41;</span>
<span style="color: #ff4500;">1.0</span></pre></div></div>

<p>Les floats ont aussi une autre particularité: on peut les représenter en notation scientifique:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> 6.02214078e23 <span style="color: #808080; font-style: italic;"># j'aimerais avoir une mole d'euros pour Noel</span>
6.02214078e+23</pre></div></div>

<p>Je ne l&#8217;ai jamais utilisé, et je n&#8217;ai aucune idée de si c&#8217;est utile pour nos amis scientifiques (y en a des biens). En tout cas, c&#8217;est là.</p>
<p>D&#8217;ailleurs, puisqu&#8217;on parle science, on est pas limité aux réels avec Python. On peut taper dans les nombres imaginaires (la notation utilise &#8220;j&#8221; et non pas &#8220;i&#8221;) :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> 1j + <span style="color: #ff4500;">1</span>
<span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>+1j<span style="color: black;">&#41;</span>
<span style="color: #ff4500;">1</span>
<span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>+1j<span style="color: black;">&#41;</span></pre></div></div>

<p>Et il y a même un module <a href="http://docs.python.org/2/library/math.html?highlight=math#math">math</a> dédié:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">math</span>.<span style="color: black;">sqrt</span><span style="color: black;">&#40;</span>-<span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># racine carrée FAIL</span>
Traceback <span style="color: black;">&#40;</span>most recent call last<span style="color: black;">&#41;</span>:
  File <span style="color: #483d8b;">&quot;&lt;ipython-input-99-0c96a175a174&gt;&quot;</span>, line <span style="color: #ff4500;">1</span>, <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #66cc66;">&lt;</span>module<span style="color: #66cc66;">&gt;</span>
    <span style="color: #dc143c;">math</span>.<span style="color: black;">sqrt</span><span style="color: black;">&#40;</span>-<span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span> 
<span style="color: #008000;">ValueError</span>: <span style="color: #dc143c;">math</span> domain error
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">cmath</span> <span style="color: #808080; font-style: italic;"># WIN</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">cmath</span>.<span style="color: black;">sqrt</span><span style="color: black;">&#40;</span>-<span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
1j</pre></div></div>

<p>Et tout ce petit monde est compatible ensemble:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">0</span> + <span style="color: #ff4500;">1.0</span> + <span style="color: #ff4500;">9999999999999999999999999999</span> + 1j
<span style="color: black;">&#40;</span>1e+28+1j<span style="color: black;">&#41;</span></pre></div></div>

<p>La seule chasse gardée des entiers, c&#8217;est l&#8217;indexing et le slicing:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> l = <span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">10</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span><span style="color: #ff4500;">1</span><span style="color: black;">&#93;</span>
<span style="color: #ff4500;">1</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span><span style="color: #ff4500;">1.0</span><span style="color: black;">&#93;</span>
Traceback <span style="color: black;">&#40;</span>most recent call last<span style="color: black;">&#41;</span>:
  File <span style="color: #483d8b;">&quot;&lt;ipython-input-138-3837752eec1a&gt;&quot;</span>, line <span style="color: #ff4500;">1</span>, <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #66cc66;">&lt;</span>module<span style="color: #66cc66;">&gt;</span>
    l<span style="color: black;">&#91;</span><span style="color: #ff4500;">1.0</span><span style="color: black;">&#93;</span>
<span style="color: #008000;">TypeError</span>: <span style="color: #008000;">list</span> indices must be integers, <span style="color: #ff7700;font-weight:bold;">not</span> <span style="color: #008000;">float</span>
&nbsp;
<span style="color: #66cc66;">&gt;&gt;&gt;</span> l<span style="color: black;">&#91;</span>1j<span style="color: black;">&#93;</span>
Traceback <span style="color: black;">&#40;</span>most recent call last<span style="color: black;">&#41;</span>:
  File <span style="color: #483d8b;">&quot;&lt;ipython-input-139-7a8d62312841&gt;&quot;</span>, line <span style="color: #ff4500;">1</span>, <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #66cc66;">&lt;</span>module<span style="color: #66cc66;">&gt;</span>
    l<span style="color: black;">&#91;</span>1j<span style="color: black;">&#93;</span>
<span style="color: #008000;">TypeError</span>: <span style="color: #008000;">list</span> indices must be integers, <span style="color: #ff7700;font-weight:bold;">not</span> <span style="color: #008000;">complex</span></pre></div></div>

<h2>L&#8217;éternel problème de la virgule qui part en couille</h2>
<p>Généralement, un débutant apprenant la programmation va commencer comme ça:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">4</span> / <span style="color: #ff4500;">2</span> <span style="color: #808080; font-style: italic;"># COOOL !</span>
<span style="color: #ff4500;">2</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">3</span> / <span style="color: #ff4500;">2</span> <span style="color: #808080; font-style: italic;"># WTF ?!!</span>
<span style="color: #ff4500;">1</span></pre></div></div>

<p>Donc là il va sur les forums, ne fait aucune recherche, et pose la même question que tous les débutants ont posé. Et une bonne âme répond patiemment que si il avait pris le temps de taper 3 secondes sur Google, espèce de connard d&#8217;étudiant fumeur de joint qui joue à League of Legend dans l&#8217;amphi, il aurait su que l&#8217;opération de division en Python 2.7 est une opération de division entière. Elle vire donc tout ce qu&#8217;il y a après la virgule.</p>
<p>Pour y remédier, il y a plusieurs possibilités.</p>
<p>1 &#8211; Utiliser des floats :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">3</span>. / <span style="color: #ff4500;">2</span>.
<span style="color: #ff4500;">1.5</span></pre></div></div>

<p>2 &#8211; Utiliser <code>truediv</code> :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">operator</span> <span style="color: #ff7700;font-weight:bold;">import</span> truediv
<span style="color: #66cc66;">&gt;&gt;&gt;</span> truediv<span style="color: black;">&#40;</span><span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
<span style="color: #ff4500;">1.5</span></pre></div></div>

<p>3 &#8211; utiliser le comportement de Python 3 :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">__future__</span> <span style="color: #ff7700;font-weight:bold;">import</span> division <span style="color: #808080; font-style: italic;"># c'est quand même la classe</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">3</span> / <span style="color: #ff4500;">2</span> <span style="color: #808080; font-style: italic;"># comportement naturel</span>
<span style="color: #ff4500;">1.5</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">3</span> // <span style="color: #ff4500;">2</span> <span style="color: #808080; font-style: italic;"># division entière</span>
<span style="color: #ff4500;">1</span></pre></div></div>

<p>Utilisez la solution 1 dans le shell pour faire vite fait, la 2 si vous modifiez un programme existant, et la 3 quand vous créer un nouveau programme. </p>
<p>Bien, revenons à notre connard de joint qui fume de l&#8217;amphi en cours de League of Legend. Il va maintenant vouloir se faire la main, et se lancer dans la création d&#8217;applications qui manquent comme des annuaires, des todo lists et des gestionnaires de budget. Sur ces derniers, il va bien entendu manipuler des sous, et les sous, il faut que ça soit précis. Alors quand il tombe là dessus:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff4500;">0.1</span> + <span style="color: #ff4500;">0.1</span> + <span style="color: #ff4500;">0.1</span> - <span style="color: #ff4500;">0.3</span> <span style="color: #808080; font-style: italic;"># ZERO !!!</span>
5.551115123125783e-17
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">print</span> <span style="color: #483d8b;">&quot;O_o dah FUCK ?&quot;</span>
O_o dah FUCK <span style="color: #66cc66;">?</span></pre></div></div>

<p>Il retourne sur le forum où on l&#8217;avait si gentiment aidé, pour refaire exactement ce qu&#8217;on lui avait dit de pas faire. Et le bon con de service (le geek de niveau intermédiaire qui est pas encore lassé de répondre aux débutants car il l&#8217;était il y a encore pas si longtemps alors il comprend, lui, pas comme ces snobs élitistes agressifs qu&#8217;il jure ne jamais devenir ce qu&#8217;il deviendra bien entendu après 6 mois de hotline gratuite sur le forum de commentcamarche.com) va lui répondre que si il avait cherché sur Google&#8230;</p>
<p>Il aurait donc vu que les ordinateurs représentent tout en base 2, et que certains nombres à virgules ne peuvent être qu&#8217;approximés.</p>
<p>Stupeur, effroi, affolement. Comment calculer le budget litière de sa coloc dans son super programme ?</p>
<p>Dans un autre langage, on lui recommanderait de tout multiplier par 100000 puis de tout diviser par 100000, pour être bien sûr.</p>
<p>En Python, il y a un module pour ça™</p>
<h2>Décimaux et fractions</h2>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">decimal</span> <span style="color: #ff7700;font-weight:bold;">import</span> Decimal
<span style="color: #66cc66;">&gt;&gt;&gt;</span> Decimal<span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;0.1&quot;</span><span style="color: black;">&#41;</span> + Decimal<span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;0.1&quot;</span><span style="color: black;">&#41;</span> + Decimal<span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;0.1&quot;</span><span style="color: black;">&#41;</span> - Decimal<span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;0.3&quot;</span><span style="color: black;">&#41;</span>
Decimal<span style="color: black;">&#40;</span><span style="color: #483d8b;">'0.0'</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Joie. Bonheur. Victoire de l&#8217;homme sur la machine et le boudin blanc.</p>
<p>On peut même définir jusqu&#8217;à quel point on veut être précis (en gros à partir de quand il arrondit) :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">decimal</span> <span style="color: #ff7700;font-weight:bold;">import</span> getcontext
<span style="color: #66cc66;">&gt;&gt;&gt;</span> getcontext<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>.<span style="color: black;">prec</span> = <span style="color: #ff4500;">6</span> <span style="color: #808080; font-style: italic;"># largement suffisant si vous n'êtes pas Paypal ou le Fisc</span></pre></div></div>

<p>Pour les nostalgiques de Javascript ou de Buzz l&#8217;éclair, on peut même créer Not A Number et l&#8217;infini:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> Decimal<span style="color: black;">&#40;</span><span style="color: #483d8b;">'NaN'</span><span style="color: black;">&#41;</span>
Decimal<span style="color: black;">&#40;</span><span style="color: #483d8b;">'NaN'</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> Decimal<span style="color: black;">&#40;</span><span style="color: #483d8b;">'-Infinity'</span><span style="color: black;">&#41;</span>
Decimal<span style="color: black;">&#40;</span><span style="color: #483d8b;">'-Infinity'</span><span style="color: black;">&#41;</span></pre></div></div>

<p>(<code>float()</code> le permet aussi, mais je vous le déconseille : le résultat est dépendant de l&#8217;implémentation)</p>
<p>Je vous invite à lire <a href="http://docs.python.org/2/library/decimal.html">la doc</a>, car il y a pas mal de choses à savoir si on veut éviter certains pièges.</p>
<p>Bref, le module <code>Decimal</code> permet de calculer avec le minimum d&#8217;approximation, évitant les erreurs d&#8217;arrondie et vous infusant de ce sentiment (fugace) que vous maîtrisez ce que vous faites. Vous pouvez manipuler des sous. Enfin presque. Car il y a évidement ensuite la douloureuse question des devises, mais la réponse à ce problème est un à <a href="http://pypi.python.org/pypi/python-money">pip install</a> de là et dépasse les considérations de cet article.</p>
<p>Donc, pour tout ce qui a beson d&#8217;être précis au poil de cul, vous allez utiliser <code>Decimal</code>. Ou pas.</p>
<p>Car <code>Decimal</code> est lent. 100 fois plus lent qu&#8217;un float environ. Alors, pour la compta, ça va. Pour le séquençage ADN d&#8217;une patate, qui je le rappelle, <a href="http://sametmax.com/a-imprimer-et-a-mettre-en-poster-dans-le-bureau-de-votre-boite/">a plus de chromosomes que nous</a>, la biatch, c&#8217;est moyen.</p>
<p>Et là, pour pallier ce genre de truc, il faut taper dans l&#8217;extension en C, donc <a href="http://sametmax.com/votre-python-aime-les-pip/">installer</a> un module comme <a href="http://www.bytereef.org/mpdecimal/index.html">cdecimal</a> (qui a la même API, il suffit ensuite de remplacer les imports) ou encore plus rapide, <a href="http://code.google.com/p/gmpy/">gmpy</a> (API différente).</p>
<p>Bon, j&#8217;en ai jamais eu besoin dans toute ma vie, <code>Decimal</code> me suffit largement. Il calcule toujours plus vite que moi sur <del>Excel</del> <del>OpenOffice</del> LibreOffice. Mais je suis sûr qu&#8217;il y a des biologistes qui ne peuvent pas faire sans, hein. Vu la communauté qu&#8217;il y a sur <a href="http://www.scipy.org/">scipy</a>, la lib de calculs scientifiques haute performance, je ne doute pas de la question.</p>
<p>Pour finir sur une note plus légère, sachez que Python permet aussi de manipuler des fractions.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> fractions <span style="color: #ff7700;font-weight:bold;">import</span> Fraction
<span style="color: #66cc66;">&gt;&gt;&gt;</span> Fraction<span style="color: black;">&#40;</span><span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
Fraction<span style="color: black;">&#40;</span><span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">int</span><span style="color: black;">&#40;</span>Fraction<span style="color: black;">&#40;</span><span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span> + Fraction<span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>
<span style="color: #ff4500;">2</span></pre></div></div>

<p>Si vous êtes dans un cas où vous manipulez beaucoup de &#8220;parts de&#8221;, c&#8217;est fort pratique.</p>


feed_id: http://sametmax.com/?p=3865
title: Programmer confortablement en Python sous Windows
uri: Programmer-confortablement-en-Python-sous-Windows
url: http://sametmax.com/programmer-confortablement-en-python-sous-windows/
content:
<p>Python est un langage qui demande très peu pour programmer: pas d&#8217;IDE, de compilateur, de RAD ou autre. Juste un petit éditeur de texte (<a href="http://notepad-plus-plus.org/fr/">notepad++</a> fait très bien l&#8217;affaire) et la ligne de commande.</p>
<p>Problème, la ligne de commande est à chier sous Windows. Alors oui, vous pouvez coder dans ces conditions, mais franchement, pourquoi ne pas passer 30 minutes pour vous mettre à l&#8217;aise ?</p>
<p>Max est sous Mac, et je suis sous Ubuntu, mais c&#8217;est pas pour ça qu&#8217;on oublie nos racines. On a tous les deux commencé sous Windows. Perso, j&#8217;ai fait mes premiers clics de souris sur 3.1 (avant j&#8217;avais pas de souris :-)). Alors suivez le guide.</p>
<h2>Améliorer la console</h2>
<p>Une fois que vous avez <a href="http://www.python.org/download/releases/2.7.3/">installé Python</a> (toujours v2.7 en 32 bits. TOUJOURS), vous avez accès au shell. Premier constat, copier / coller dans un terminal cmd.exe est aussi plaisant qu&#8217;une coloscopie un lendemain de cuite (pour vous et le praticien).</p>
<p>Idéalement, il faut installer un terminal alternatif. Le logiciel opensource Console2 est parfait pour ça: on peut faire du copier / coller facilement, il a des onglets, on peut régler la taille de la fenêtre&#8230;</p>
<p>Pour l&#8217;installer suffit de <a href="http://sourceforge.net/projects/console/">télécharger le zip</a>, l&#8217;extraire dans &#8220;C:\Programmes Files&#8221; et faire un raccourci sur le bureau vers &#8220;C:\Program Files\Console2\Console.exe&#8221;.</p>
<h2>Améliorer le shell Python</h2>
<p>Le shell Python est fantastique, à l&#8217;exception de tous les autres. Donc votre premier réflexe, c&#8217;est bien entendu d&#8217;installer <a href="http://pypi.python.org/pypi/ipython">iPython</a>. Sauf que Windows n&#8217;a pas readline, du coup vous n&#8217;allez pas avoir la coloration du prompt ni la completion du code. Ca craint.</p>
<p>C&#8217;est là que <a href="http://sametmax.com/votre-python-aime-les-pip/">pip</a> va encore une fois nous sauver la mise:</p>
<p><code>pip install pyreadline</code></p>
<p>Et votre shell iPython, lancé depuis Console2 est maintenant un outil presque aussi confortable à utiliser que sous Linux ou Mac avec historique, auto indent et tout le toutim. Presque, faut pas abuser non plus.</p>
<h2>Et pour quelques outils de plus</h2>
<p>Windows n&#8217;ayant pas de truc comme grep, installer <a href="http://sametmax.com/grin-le-grep-python-sous-steroid/">grin </a>va vous permettre de rapidement et confortablement chercher dans votre code. <code>Donc, pip install grin</code>.</p>
<p>Mais aller directement dans le dossier voulu depuis la ligne de commande à grand coup de <code>cd</code>, c&#8217;est relou. On va arranger ça.</p>
<p>Ouvre l&#8217;éditeur de registre (&#8220;Windows + R&#8221; puis regedit puis &#8220;enter&#8221;) et naviguez dans l&#8217;arboresence jusqu&#8217;à:</p>
<p><code>HKEY_CLASSES_ROOT\Directory\shell\</code></p>
<p>Cliquez droit dans le panel de droite, et faites &#8220;Nouveau > Clé&#8221; et appelez la clé &#8220;open_shell&#8221;. Puis cliquez sur le dossier ainsi créé, et dans le panel de droite, cliquez sur l&#8217;espèce d&#8217;icône &#8220;AB&#8221; intitulée &#8220;(Par défaut)&#8221;, et donnez lui la valeur &#8220;Ouvrir Console2 ici&#8221;.</p>
<p>Dans le dossier &#8220;open_shell&#8221;, créez un dossier &#8220;Command&#8221; (en faisant &#8220;Clic Droit > Nouveau > Clé&#8221;).</p>
<p>Donnez à &#8220;(Par défaut)&#8221; pour valeur le chemin vers Console2 suivit de &#8216;-d &#8220;%1&#8243;&#8216;, par exemple pour moi:</p>
<p><code>"C:\Program Files (x86)\Console2\Console.exe" -d "%1"</code></p>
<p>Fermer l&#8217;explorateur de fichiers, et réouvrez le. Hop ! Vous avez une nouvelle entrée dans le menu du clic droit qui permet d&#8217;ouvrir Console2 dans n&#8217;importe quel dossier.</p>


feed_id: http://sametmax.com/?p=3875
title: Manipuler les dates et les durées en Python
uri: Manipuler-les-dates-et-les-durées-en-Python
url: http://sametmax.com/manipuler-les-dates-et-les-durees-en-python/
content:
<p>Manipuler des dates, c&#8217;est chaud. Le calendrier, c&#8217;est plein de subtilités comme les années bisextiles, les mois qui ont 4 possibilités de nombre de jours, les semaines qui commencent un dimanche aux US et un lundi en France&#8230; Autant dire que faire ça à la mano, c&#8217;est pas marrant, marrant.</p>
<p>Avec les modules <code>datetimes</code> et <code>calendar</code>, c&#8217;est déjà plus cool.</p>
<h2>Date et heure</h2>
<p><code>Datetime</code> est un module qui permet de manipuler des dates et des durées sous forme d&#8217;objets. L&#8217;idée est simple: vous manipulez l&#8217;objet pour faire tous vos calculs, et quand vous avez besoin de l&#8217;afficher, vous formattez l&#8217;objet en chaîne de caractères.</p>
<p>On peut créer artificiellement un objet <code>datetime</code>, ses paramètres sont:</p>
<p><code>datetime(année, mois, jour, heure, minute, seconde, microseconde, fuseaux horaire)</code></p>
<p>Mais seuls &#8220;année&#8221;, &#8220;mois&#8221; et &#8220;jour&#8221; sont obligatoires.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">datetime</span> <span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">datetime</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">datetime</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">datetime</span>.<span style="color: #dc143c;">datetime</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Nous sommes ici le premier janvier 2000, à la seconde et la minute zéro, de l&#8217;heure zéro.</p>
<p>On peut bien entendu récupérer l&#8217;heure et la date du jour:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant = <span style="color: #dc143c;">datetime</span>.<span style="color: black;">now</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant
<span style="color: #dc143c;">datetime</span>.<span style="color: #dc143c;">datetime</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2012</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">24</span>, <span style="color: #ff4500;">18</span>, <span style="color: #ff4500;">20</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">534918</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">year</span>
<span style="color: #ff4500;">2012</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">month</span>
<span style="color: #ff4500;">12</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">day</span>
<span style="color: #ff4500;">24</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">hour</span>
<span style="color: #ff4500;">18</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">minute</span>
<span style="color: #ff4500;">20</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">second</span>
<span style="color: #ff4500;">4</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">microsecond</span>
<span style="color: #ff4500;">534918</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">isocalendar</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># année, semaine, jour</span>
<span style="color: black;">&#40;</span><span style="color: #ff4500;">2012</span>, <span style="color: #ff4500;">52</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Enfin, si vous souhaitez uniquement vous occuper de la date ou de l&#8217;heure:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> <span style="color: #dc143c;">datetime</span> <span style="color: #ff7700;font-weight:bold;">import</span> date, <span style="color: #dc143c;">time</span>, <span style="color: #dc143c;">datetime</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> date<span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">time</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">12</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">datetime</span>.<span style="color: #dc143c;">time</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">12</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant = <span style="color: #dc143c;">datetime</span>.<span style="color: black;">now</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2012</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">25</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: #dc143c;">time</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">datetime</span>.<span style="color: #dc143c;">time</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">15</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">16</span>, <span style="color: #ff4500;">704000</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Notez que j&#8217;écris cet article le jour de Noël, en famille. Et que là mon frangin est en train d&#8217;aider ma mère à éplucher des pommes tandis que je les regarde de loin. C&#8217;est mal. Je vais leur donner un coup de main et je reviens.</p>
<p>*Sam épluche les pommes et s&#8217;efforce de se tenir éloigné du débat sur la condition des canards gavés pour leur foie. Il quitte la table discrètement dès le premier usage de wikipédia pour défendre les volatiles*</p>
<p>Back.</p>
<p>Je disais donc&#8230;</p>
<h2>Durée</h2>
<p>En plus de pouvoir récupérer la date du jour, on peut calculer la différence entre deux dates. Par exemple, combien de temps y a-t-il entre aujourd&#8217;hui et le premier jour de l&#8217;an 2000 ?</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> duree = <span style="color: #dc143c;">datetime</span>.<span style="color: black;">now</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> - <span style="color: #dc143c;">datetime</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> duree
<span style="color: #dc143c;">datetime</span>.<span style="color: black;">timedelta</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">4741</span>, <span style="color: #ff4500;">66999</span>, <span style="color: #ff4500;">829132</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Et vous découvrez ici un autre objet: le <code>timedelta</code>. Cet objet représente une durée en jours, secondes et microsecondes.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> duree.<span style="color: black;">days</span>
<span style="color: #ff4500;">4741</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> duree.<span style="color: black;">seconds</span>
<span style="color: #ff4500;">67007</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> duree.<span style="color: black;">mi</span>
duree.<span style="color: black;">microseconds</span>  duree.<span style="color: #008000;">min</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> duree.<span style="color: black;">microseconds</span>
<span style="color: #ff4500;">943760</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> duree.<span style="color: black;">total_seconds</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># addition de toutes les secondes + les jours</span>
<span style="color: #ff4500;">409689407.94376</span></pre></div></div>

<p>On peut créer son propre <code>timedelta</code>:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> timedelta<span style="color: black;">&#40;</span>days=<span style="color: #ff4500;">3</span>, seconds=<span style="color: #ff4500;">100</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">datetime</span>.<span style="color: black;">timedelta</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">100</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Cela permet de répondre à la question : &#8220;Quelle date serons-nous dans 2 jours, 4 heures, 3 minutes, et 12 secondes ?&#8221;:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">datetime</span>.<span style="color: black;">now</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> + timedelta<span style="color: black;">&#40;</span>days=<span style="color: #ff4500;">2</span>, hours=<span style="color: #ff4500;">4</span>, minutes=<span style="color: #ff4500;">3</span>, seconds=<span style="color: #ff4500;">12</span><span style="color: black;">&#41;</span>
<span style="color: #dc143c;">datetime</span>.<span style="color: #dc143c;">datetime</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2012</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">26</span>, <span style="color: #ff4500;">22</span>, <span style="color: #ff4500;">44</span>, <span style="color: #ff4500;">6</span>, <span style="color: #ff4500;">251071</span><span style="color: black;">&#41;</span></pre></div></div>

<p>A chaque fois, un nouvel objet est retourné. En effet, les objets <code>datetime</code> et <code>timedelta</code> sont immutables. Ainsi si vous voulez utiliser une version légèrement différente d&#8217;un objet <code>datetime</code>, il faudra toujours en créer un nouveau. Par exemple:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant = <span style="color: #dc143c;">datetime</span>.<span style="color: black;">now</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> maintenant.<span style="color: black;">replace</span><span style="color: black;">&#40;</span>year=<span style="color: #ff4500;">1995</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># on créer un nouvel objet</span>
<span style="color: #dc143c;">datetime</span>.<span style="color: #dc143c;">datetime</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1995</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">25</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">9</span>, <span style="color: #ff4500;">46</span>, <span style="color: #ff4500;">185000</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Vous noterez que je ne parles pas de fuseaux horaire. Et bien c&#8217;est parceque l&#8217;implémentation Python est particulièrement ratée : l&#8217;API est compliquée et les données ne sont pas à jour. Il faut dire que la mesure du temps, contrairement à ce qu&#8217;on pourrait penser, n&#8217;est pas vraiment le truc le plus stable du monde, et des pays <a href="http://www.rfi.fr/asie-pacifique/20111230-iles-samoa-fuseau-horaire">changent régulièrement leur manière de faire</a>.</p>
<p>Donc je trollerai sur fuseaux dans un article plus gluant sur lequel, une fois n&#8217;est pas coutume, je taclerai Python. Restons sur les dates pures.</p>
<h2>Autre modules</h2>
<p>Une fois que vous maitrisez <code>datetime</code>, vous pouvez retourner lire notre article sur le <a href="http://sametmax.com/serialiser-et-parser-une-date-en-python-formats-de-strftimestrptime-et-timestamps/">formatage de date</a>.</p>
<p>Mais ce n&#8217;est pas tout, il y d&#8217;autres modules liées à la gestion du temps en Python.</p>
<p>Dans la lib standard, il y a <a href="http://docs.python.org/2/library/calendar.html?highlight=calendar#calendar">calendar</a>.</p>
<p>Il permet de manipuler un calendrier comme un objet, et itérer sur les jours d&#8217;un mois, les semaines, verifier les caractéristiques d&#8217;un jour en particulier, etc. :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">import</span> <span style="color: #dc143c;">calendar</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">calendar</span>.<span style="color: black;">mdays</span> <span style="color: #808080; font-style: italic;"># combien de jour par mois ?</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">31</span>, <span style="color: #ff4500;">28</span>, <span style="color: #ff4500;">31</span>, <span style="color: #ff4500;">30</span>, <span style="color: #ff4500;">31</span>, <span style="color: #ff4500;">30</span>, <span style="color: #ff4500;">31</span>, <span style="color: #ff4500;">31</span>, <span style="color: #ff4500;">30</span>, <span style="color: #ff4500;">31</span>, <span style="color: #ff4500;">30</span>, <span style="color: #ff4500;">31</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">calendar</span>.<span style="color: black;">isleap</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># est-ce une année bisextile ?</span>
<span style="color: #008000;">True</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">calendar</span>.<span style="color: black;">weekday</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># quel jour était cette date ?</span>
<span style="color: #ff4500;">5</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">calendar</span>.<span style="color: black;">MONDAY</span>, <span style="color: #dc143c;">calendar</span>.<span style="color: black;">TUESDAY</span>, <span style="color: #dc143c;">calendar</span>.<span style="color: black;">WEDNESDAY</span>, <span style="color: #dc143c;">calendar</span>.<span style="color: black;">THURSDAY</span>, <span style="color: #dc143c;">calendar</span>.<span style="color: black;">FRIDAY</span>, <span style="color: #dc143c;">calendar</span>.<span style="color: black;">SATURDAY</span>, <span style="color: #dc143c;">calendar</span>.<span style="color: black;">SUNDAY</span> 
<span style="color: black;">&#40;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span>, <span style="color: #ff4500;">6</span><span style="color: black;">&#41;</span></pre></div></div>

<p>On peut instancier un calendrier et itérer dessus:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> cal = <span style="color: #dc143c;">calendar</span>.<span style="color: black;">Calendar</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> cal.<span style="color: black;">getfirstweekday</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #ff4500;">0</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">list</span><span style="color: black;">&#40;</span>cal.<span style="color: black;">iterweekdays</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>
<span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span>, <span style="color: #ff4500;">6</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">list</span><span style="color: black;">&#40;</span>cal.<span style="color: black;">itermonthdays</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span> 
<span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span>, <span style="color: #ff4500;">6</span>, <span style="color: #ff4500;">7</span>, <span style="color: #ff4500;">8</span>, <span style="color: #ff4500;">9</span>, <span style="color: #ff4500;">10</span>, <span style="color: #ff4500;">11</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">13</span>, <span style="color: #ff4500;">14</span>, <span style="color: #ff4500;">15</span>, <span style="color: #ff4500;">16</span>, <span style="color: #ff4500;">17</span>, <span style="color: #ff4500;">18</span>, <span style="color: #ff4500;">19</span>, <span style="color: #ff4500;">20</span>, <span style="color: #ff4500;">21</span>, <span style="color: #ff4500;">22</span>, <span style="color: #ff4500;">23</span>, <span style="color: #ff4500;">24</span>, <span style="color: #ff4500;">25</span>, <span style="color: #ff4500;">26</span>, <span style="color: #ff4500;">27</span>, <span style="color: #ff4500;">28</span>, <span style="color: #ff4500;">29</span>, <span style="color: #ff4500;">30</span>, <span style="color: #ff4500;">31</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">list</span><span style="color: black;">&#40;</span>cal.<span style="color: black;">itermonthdates</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>
<span style="color: black;">&#91;</span><span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1999</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">27</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1999</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">28</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1999</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">29</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1999</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">30</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1999</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">31</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">4</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">5</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">6</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">7</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">8</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">9</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">10</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">11</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">12</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">13</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">14</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">15</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">16</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">17</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">18</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">19</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">20</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">21</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">22</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">23</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">24</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">25</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">26</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">27</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">28</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">29</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">30</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">31</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">4</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">5</span><span style="color: black;">&#41;</span>, <span style="color: #dc143c;">datetime</span>.<span style="color: black;">date</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">2</span>, <span style="color: #ff4500;">6</span><span style="color: black;">&#41;</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> cal.<span style="color: black;">monthdayscalendar</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">2000</span>, <span style="color: #ff4500;">1</span><span style="color: black;">&#41;</span>
<span style="color: black;">&#91;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#93;</span>, <span style="color: black;">&#91;</span><span style="color: #ff4500;">3</span>, <span style="color: #ff4500;">4</span>, <span style="color: #ff4500;">5</span>, <span style="color: #ff4500;">6</span>, <span style="color: #ff4500;">7</span>, <span style="color: #ff4500;">8</span>, <span style="color: #ff4500;">9</span><span style="color: black;">&#93;</span>, <span style="color: black;">&#91;</span><span style="color: #ff4500;">10</span>, <span style="color: #ff4500;">11</span>, <span style="color: #ff4500;">12</span>, <span style="color: #ff4500;">13</span>, <span style="color: #ff4500;">14</span>, <span style="color: #ff4500;">15</span>, <span style="color: #ff4500;">16</span><span style="color: black;">&#93;</span>, <span style="color: black;">&#91;</span><span style="color: #ff4500;">17</span>, <span style="color: #ff4500;">18</span>, <span style="color: #ff4500;">19</span>, <span style="color: #ff4500;">20</span>, <span style="color: #ff4500;">21</span>, <span style="color: #ff4500;">22</span>, <span style="color: #ff4500;">23</span><span style="color: black;">&#93;</span>, <span style="color: black;">&#91;</span><span style="color: #ff4500;">24</span>, <span style="color: #ff4500;">25</span>, <span style="color: #ff4500;">26</span>, <span style="color: #ff4500;">27</span>, <span style="color: #ff4500;">28</span>, <span style="color: #ff4500;">29</span>, <span style="color: #ff4500;">30</span><span style="color: black;">&#93;</span>, <span style="color: black;">&#91;</span><span style="color: #ff4500;">31</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span>, <span style="color: #ff4500;">0</span><span style="color: black;">&#93;</span><span style="color: black;">&#93;</span></pre></div></div>

<p>Comme souvent Python vient aussi avec de très bons modules tierces parties pour manipuler les dates:</p>
<ul>
<li><a href="http://labix.org/python-dateutil">dateutils</a> est un datetime boosté aux hormones qui permet notament de donnée des durées floues comme &#8220;+ 1 mois&#8221; et gérer des événements qui se répètent. Il est dans tous mes projets par défaut.</li>
<li><a href="http://babel.edgewall.org/">babel</a> n&#8217;est pas spécialisé dans les dates mais dans la localisation. Le module possèdes des outils pour formatter des dates selon le format de chaque pays, et aussi avec des formats naturels comme &#8220;il y a une minute&#8221;.</li>
<li><a href="http://pypi.python.org/pypi/pytz">pytz</a> est une implémentation saine de gestion des fuseaux horaires en Python. On y reviendra.</li>
</ul>


feed_id: http://sametmax.com/?p=3887
title: L’opérateur NOT bitwise “~” (ou tilde) en Javascript
uri: L-opérateur-NOT-bitwise-(ou-tilde)-en-Javascript
url: http://sametmax.com/loperateur-not-bitwise-ou-tilde-en-javascript/
content:
<p>L&#8217;opérateur NOT bitwise est en général utilisé comme un <code>Math.floor()</code>, en plus rapide. Mais il a une propriété amusante sur les entiers, il les transforme en <code>-(N+1)</code>, où N est l&#8217;entier en question.</p>
<p>La conséquence ?</p>
<pre>~-2 => 1
~-1 => 0
~0 => -1
~1 => -2
~2 => -3</pre>
<p>Or, en javascript on a un problème avec le fait que la seule option pour rechercher un élément dans un ensemble soit des fonctions comme <code>indexOf</code> qui retournent l&#8217;index de ce qu&#8217;elles trouvent ou <code>-1</code>, les chiennes.</p>
<p>Ce qui fait que:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;truc&quot;</span>.<span style="color: #660066;">indexOf</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'t'</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'trouvé'</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Ne va rien afficher, car <code>'t'</code> est à la première place, renvoyant l&#8217;index <code>0</code>, qui est &#8220;faux&#8221; dans un contexte booléan. Mais :</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;truc&quot;</span>.<span style="color: #660066;">indexOf</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'z'</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'trouvé'</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Va afficher &#8220;trouvé&#8221; car la fonction renvoit <code>-1</code> quand elle ne trouve rien. C&#8217;est nul. On se retrouve donc à faire du :</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;truc&quot;</span>.<span style="color: #660066;">indexOf</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'z'</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">&gt;</span> <span style="color: #339933;">-</span><span style="color: #CC0000;">1</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'trouvé'</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Ce qui est moche comme ça en peut plus. Mais avec l&#8217;opérateur bitwise, <code>0</code> devient <code>-1</code> (donc vrai, comme tous les autres chiffres) et <code>-1</code> devient zéro.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>~<span style="color: #3366CC;">&quot;truc&quot;</span>.<span style="color: #660066;">indexOf</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'t'</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    console.<span style="color: #660066;">log</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'trouvé'</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Et là ça va marcher !</p>
<p>Vous venez officiellement de passer 10 minutes sur un article qui va vous faire gagner 1 seconde sur l&#8217;ensemble de votre vie. En fait même pas, car pour garder votre code lisible, je vous recommande de ne pas utiliser cette technique. </p>
<p>De rien.</p>


feed_id: http://sametmax.com/?p=3893
title: Les robots pourraient-ils remplacer les prostituées ?
uri: Les-robots-pourraient-ils-remplacer-les-prostituées
url: http://sametmax.com/les-robots-pourraient-t-ils-remplacer-les-prostituees/
content:
<p>L&#8217;existence des <a href="http://www.realdoll.com/cgi-bin/snav.rd?action=viewpage&amp;section=frealdoll2">realdolls sur mesure</a> laisser penser que la poupée gonflable hi-tech peut encore largement se développer. Or, les robots que nous fabriquons sont de plus en plus perfectionnés:</p>

<!-- iframe plugin v:2.3 - wordpress.org/extend/plugins/iframe/ -->
<iframe width="540" height="360" src="http://www.youtube.com/embed/J71XWkh80nc?feature=player_embedded" frameborder="0" scrolling="no" class="iframe-class"></iframe>
<p>On pourrait donc très bien passer plus rapidement que l&#8217;on le pense du malaise de l&#8217;<a href="https://fr.wikipedia.org/wiki/Vall%C3%A9e_d%C3%A9rangeante">uncanny valley</a> vers une <a href="http://www.allocine.fr/film/fichefilm_gen_cfilm=43242.html">acceptation des cyber-chattes</a> dans nos foyers.</p>
<p>Grâce à la fameuse règle 34, on a très vite eu des robots sexy, mais là avec la deferlante de standardisation américaine de la dernière décennie, c&#8217;est carrément un meca-harem multimédia qu&#8217;Hollywood produit tous les jours. Ca n&#8217;a pas l&#8217;air de déranger le chaland.</p>
<div id="attachment_3894" class="wp-caption aligncenter" style="width: 410px"><a href="http://sametmax.com/wp-content/uploads/2012/12/gracepark009-400-x-492.jpg"?9d7bd4"><img class="size-full wp-image-3894" title="Dans BG, ils sont payé un supplément pour l'option &quot;mon sex toy ne sait pas qu'il est un robot&quot;" src="http://sametmax.com/wp-content/uploads/2012/12/gracepark009-400-x-492.jpg"?9d7bd4" alt="Photo d'un cylon sexy" width="400" height="492" /></a><p class="wp-caption-text">Dans BG, ils sont payé un supplément pour l&#39;option &quot;mon sex toy ne sait pas qu&#39;il est un robot&quot;</p></div>
<h2>Causes</h2>
<p>La plastipute coutera cher (déjà les realdolls, c&#8217;est dans les 3000 real dol), certes, mais l&#8217;investissement se fera une seule fois. Pour les proxénètes, c&#8217;est un gain net en entretien et en vol de passeports. Pour le particulier, c&#8217;est un prix dégressif voir la possibilité de posséder son propre modèle à la maison, rapidement rentabilisé pour le gros consommateur. Le rapport euro / ejac sera donc un des premiers motivateurs.</p>
<p>Un autre sera évidement la fainéantise / timidité / pression sociale qui fait qu&#8217;aller dans les bars pour se prendre 30 râteaux en écoutant du mauvais alcool et en buvant de la mauvaise musique avec glaçons ne fera pas le poids face à la perspective de tirer son coup immédiatement avec un canon customisé. Et on a pas à aller demander &#8220;c&#8217;est combien&#8221; à une personne réelle, c&#8217;est toujours ça de gagné.</p>
<p>En plus de la facilité, il y a l&#8217;hygiène: pas de MST (on peut créer des vaginous auto lavant), pas de parfum qui reste collé dans les cheveux détectés immédiatement par la gente féminine, pas de capote à mettre, pas de problème pour la sodomie. Hey, vous pouvez lui-même dans l&#8217;oreille si ça vous amuse.</p>
<div id="attachment_3895" class="wp-caption aligncenter" style="width: 475px"><a href="http://sametmax.com/wp-content/uploads/2012/12/summer-glau-the-sarah-connor-chronicles-sexy-L-2.jpeg"?9d7bd4"><img class="size-full wp-image-3895" title="Nan je suis pas Jonh connor, mais tu peux rentrer quand même !" src="http://sametmax.com/wp-content/uploads/2012/12/summer-glau-the-sarah-connor-chronicles-sexy-L-2.jpeg"?9d7bd4" alt="Photo sexy d'un des terminators de la série Sarah Connor's Chronicles" width="465" height="567" /></a><p class="wp-caption-text">Nan je suis pas Jonh connor, mais tu peux rentrer quand même !</p></div>
<h2>Conséquences</h2>
<p>La prostitution et les MST vont en prendre un méchant coup. Elles ne disparaitrons jamais, car l&#8217;humanité est pleine de niches, mais l&#8217;homo sapiens choisissant toujours la facilité, on peut fort parier que si le service rendu est suffisamment similaire à l&#8217;original avec moins d&#8217;inconvénients (voir aussi: plats surgelés, chats sur internet, cartes cadeaux&#8230;) le succès sera au rendez-vous.</p>
<p>La frustration sexuelle diminuant, on devrait voir alors venir une diminution de l&#8217;agressivité générale, de compétitivité entre mâles, et globalement d&#8217;activité. Car quand un mec a un orgasme, il part généralement pas manifester juste derrière pour les retraites. Il faut que j&#8217;en touche deux mots au gouvernement.</p>
<p>Mais la partie la plus fun serait sans doute la conséquence sur la drague: les mecs le font principalement pour tirer un coup, pas pour créer une relation. Or comme:</p>
<ul>
<li>c&#8217;est contraignant;</li>
<li>ce sont les mecs qui doivent faire le premiers pas;</li>
<li>des tas de situations (soirées, bars, boîtes, etc) attirent les mecs uniquement pour ça;</li>
</ul>
<p>On pourrait voir un sorte de renversement. Plus de mecs dans les bars ou les boîtes (à part pour un verre entre potes), plus de soirées consensuelles chiantes, et surtout moins de mecs qui s&#8217;emmerderont ne serait-ce qu&#8217;à parler à une nana des trucs qui ne l&#8217;intéresse pas.</p>
<div id="attachment_3898" class="wp-caption aligncenter" style="width: 308px"><a href="http://sametmax.com/wp-content/uploads/2012/12/32839.jpg"?9d7bd4"><img class="size-full wp-image-3898" title="Jodo et Moebius ont vraiment été visionaire avec le scénario de l'Incal" src="http://sametmax.com/wp-content/uploads/2012/12/32839.jpg"?9d7bd4" alt="Couverture d'un des tomes de l'incal" width="298" height="400" /></a><p class="wp-caption-text">Jodo et Moebius ont vraiment été visionnaires avec le scénario de l&#39;Incal</p></div>
<p>Alors on va me dire &#8220;oui, mais les relations humaines, l&#8217;amour, et tout ?&#8221;. Ben ce sera comme avant. Ca, c&#8217;est le seul truc qui ne changera pas. Car déjà c&#8217;est minable dans notre société: les gens se rencontrent et restent ensemble pour des raisons superficielles, dans la grande majorité des cas. Le neurodildo bipède ne va faire que retirer ces interactions qui donnent l’illusion que les gens en ont quelques choses à foutre.</p>
<p>Ne restera alors que les gens qui font des activités parce qu&#8217;ils en ont envie, qui vont parler aux gens parce qu&#8217;ils sont sociables, etc. Pas beaucoup. Mais il n&#8217;y en a jamais eu beaucoup.</p>
<p>Devenir riche ne rend pas con, il révèle simplement ce que l&#8217;on est quand on a plus besoin de faire semblant d&#8217;être gentil. Ce sera pareil avec le monde entier qui aura les couilles vides. Enfin le monde entier, les pays riches qui pourront se payer les toys créés par des enfants du tiers monde via <a href="https://secure.huffingtonpost.com/2011/05/06/apple-foxconn-suicide-pact_n_858504.html">Foxconn</a>, qui aura un partenariat pour le futur iBonne, avec une nouvelle connectique incompatible avec l&#8217;ancienne.</p>
<p>Et la bonne nouvelle, c&#8217;est que tout comme Facebook a laissé le champ libres aux personnes sociables pour créer des liens encore plus facilement en n&#8217;étant tout simplement pas sur le site et en parlant aux gens, les SexDroids vont permettre à vous et à moi de pouvoir mettre une cartouche à de la galinette cendrée avec pédigrée car plus personne ne s&#8217;en occupera.</p>
<p>J&#8217;ai hâte d&#8217;y être.</p>
<h2>Questions existentielles</h2>
<p>La conjointe acceptera-t-elle le sex toy sur pattes grandeur nature plus belle qu&#8217;elle (et plus sollicité) dans le foyer comme on a fini par trouver le godmichet banal ?</p>
<p>Si oui, en sera-t-elle jalouse ?</p>
<p>Les robots vont-ils devenirs suffisamment conscients pour avoir des droits et porter plainte pour viol ou esclavagisme sexuels ?</p>
<p>Qui va vider la poche à sperme du robot quand elle sera pleine comme un sac d&#8217;aspirateur ?</p>
<p>Y aura-t-il des magasins de vente d&#8217;occasion d&#8217;accessoires spécialement pour les prostituées mécaniques ? Seront-ils moins chers car peu utilisés et en très bon état ?</p>
<p>Pourrez-vous amenez la votre à un réveillons du nouvel an ? Et à une soirée mousse ?</p>
<p>Quel impact sur l&#8217;industrie du porno ? Pourra-t-on voir des hybrides humain-animal en vrai comme dans les hentaïs ?</p>
<p>Des perspectives qui vont vraiment dans le sens d&#8217;une remise en cause profonde de notre société. Le commercial et le législateur vont avoir fort à faire.</p>
<p>&nbsp;</p>
<div id="attachment_3906" class="wp-caption aligncenter" style="width: 483px"><a href="http://sametmax.com/wp-content/uploads/2012/12/necomimi.jpg"?9d7bd4"><img class=" wp-image-3906  " title="Ce truc exite. Il est réel. Des gens l'achètent. Avec du vrai argent. Baise-t-il avec ?" src="http://sametmax.com/wp-content/uploads/2012/12/necomimi.jpg"?9d7bd4" alt="Photo d'une fille portant un necomimmi" width="473" height="404" /></a><p class="wp-caption-text">Ce truc existe. Il est réel. Des gens l&#39;achètent. Avec du vrai argent. Baisent-t-ils avec ?</p></div>


feed_id: http://sametmax.com/?p=3916
title: Mettez vos sites Web et apps en plein écran avec l’API HTML 5 fullscreen
uri: Mettez-vos-sites-Web-et-apps-en-plein-écran-avec-l-API-HTML-5-fulls
url: http://sametmax.com/utiliser-lapi-html5-fullscreen-pour-mettre-votre-site-app-en-plein-ecran/
content:
<p>Il est loin le temps où le JS était un sous langage utilisé uniquement par des deumeurés en mal de &lt;blink&gt;. Maintenant c&#8217;est un sous langage utilisé par des gens très sérieux. PHP l&#8217;a bien prouvé, on peut être parfaitement utile en ayant une syntaxe daubée, et Javascript se pare donc de tout un tas de trucs surpuissants en ces temps de HTML5, CSS3 et Rambo8.</p>
<p>Fini donc le temps où votre site restait prisonnier de son canvas en 800&#215;600, maintenant votre dernière application de calcul de budget de croquettes pour hérisson peut enfin s&#8217;exprimer dans toute la hauteur et la largeur d&#8217;un écran Retanal grâce à <code>requestFullscreen()</code>, qui va vous permettre &#8230; d&#8217;appuyer sur F11 à la place de l&#8217;utilisateur.</p>
<p>Mais il aura à faire un clic de confirmation quand même. Car il aura un gros prompt bien alarmant avant. Le progrès je vous dis !</p>
<h2>Le code, en 2 / 2</h2>
<p>Parce que bien entendu c&#8217;est incompatible avec les tondeuses à gazons et que selon les marques de votre pétrolettes, le prefix ne sera pas le même, on va commencer par vérifier le support du bouzin.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> supportFullScreen<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    <span style="color: #003366; font-weight: bold;">var</span> doc <span style="color: #339933;">=</span> document.<span style="color: #660066;">documentElement</span><span style="color: #339933;">;</span>
    <span style="color: #000066; font-weight: bold;">return</span> <span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'requestFullscreen'</span> <span style="color: #000066; font-weight: bold;">in</span> doc<span style="color: #009900;">&#41;</span> <span style="color: #339933;">||</span> <span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'mozRequestFullScreen'</span> <span style="color: #000066; font-weight: bold;">in</span> doc <span style="color: #339933;">&amp;&amp;</span> document.<span style="color: #660066;">mozFullScreenEnabled</span><span style="color: #009900;">&#41;</span> <span style="color: #339933;">||</span> <span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'webkitRequestFullScreen'</span> <span style="color: #000066; font-weight: bold;">in</span> doc<span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Puis on va demander à l&#8217;utilisateur si on a le droit, s&#8217;il-te-plait-pitié-déconne-pas-putain, de mettre votre site en plein écran. Car figurez vous qu&#8217;il y a un sérieux risque de phishing, comme en voici <a href="http://feross.org/html5-fullscreen-api-attack/">la démonstration rigolote</a>.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> requestFullScreen<span style="color: #009900;">&#40;</span>elem<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>elem.<span style="color: #660066;">requestFullscreen</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        elem.<span style="color: #660066;">requestFullscreen</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span> <span style="color: #000066; font-weight: bold;">else</span> <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>elem.<span style="color: #660066;">mozRequestFullScreen</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        elem.<span style="color: #660066;">mozRequestFullScreen</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span> <span style="color: #000066; font-weight: bold;">else</span> <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>elem.<span style="color: #660066;">webkitRequestFullScreen</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
        elem.<span style="color: #660066;">webkitRequestFullScreen</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Ca s&#8217;utilise ainsi:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">requestFullScreen<span style="color: #009900;">&#40;</span>document.<span style="color: #660066;">body</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>A ce moment là l&#8217;écran de le navigateur passe en plein écran avec un gros panel d&#8217;avertissement genre &#8220;le certificat du site est invalide&#8221;, mais en gris. Et si l&#8217;utilisateur lit le message avant de se ruer sur le bouton &#8220;annuler&#8221; par réflexe, il s’apercevra qu&#8217;on lui explique ce qui se passe pour pas qu&#8217;il finisse de mourir de sa crise cardiaque.</p>
<p>Vous pouvez utiliser n&#8217;importe quel autre élément que <code>body</code>, et donc mettre en plein écran de tout petit widgets. Attention cependant, il va prendre la taille de tout l&#8217;écran, déclenchant tout un tas d&#8217;events de changement de taille, de display, changeant les overflows et gagnant un style par défaut qui sera différent selon le navigateur. Le W3C a un deal avec les browser vendors pour s&#8217;assurer que les devs Web ne soient jamais prêt d&#8217;être au chômage.</p>
<p>Passons.</p>
<p>Le problème quand on demande, c&#8217;est qu&#8217;on peut se voir répondre &#8220;non&#8221;. Donc en prime, il vaut mieux se concocter un fallback si jamais mémé s&#8217;affole devant la menace de voir ses onglets avalés par le viewport. Ici, je vous pond ça en jQuery, parceque la gestion des events à la main, c&#8217;est juste relou.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span> onFullScreenEvent<span style="color: #009900;">&#40;</span>callback<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    $<span style="color: #009900;">&#40;</span>document<span style="color: #009900;">&#41;</span>.<span style="color: #660066;">live</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">&quot;fullscreenchange mozfullscreenchange webkitfullscreenchange&quot;</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
        callback<span style="color: #009900;">&#40;</span>document.<span style="color: #660066;">fullscreen</span> <span style="color: #339933;">||</span> document.<span style="color: #660066;">mozFullScreen</span> <span style="color: #339933;">||</span> document.<span style="color: #660066;">webkitIsFullScreen</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
    <span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>Bon, normalement on utilise &#8216;on()&#8217; maintenant chez les gens branchés, mais j&#8217;arrive à le faire marche une fois sur deux. Donc ça s&#8217;utilise comme ça:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">onFullScreenEvent<span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>isFullscreen<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    faire un truc selon que l<span style="color: #3366CC;">'on est en fullscreen ou pas, comme pousser mémé dans les orties
});</span></pre></div></div>

<h2>Clusions ensemble entre cons</h2>
<p>Et voilà, vous avez une application fullscreenable. Il ne vous reste plus rien à faire. A part rajouter un bouton pour le permettre à l&#8217;utilisateur de mettre en fullscreen. Puis un autre pour sortir du fullscreen. Puis de gérer la transition des états de votre app. Les différences de rendu selon la taille des éléments et du style par défaut appliqué par le navigateur. Et bien entendu le plus dur: faire comprendre tout ce bordel à votre utilisateur final.</p>
<p>Plus rien à faire je vous dis: on vous a mâché le travail.</p>
<p>Si vous avez pas le temps, vous pouvez aussi mettre <code>alert('appuyez sur F11 pour passer en plein écran')</code>. Mais bon, j&#8217;écrirais des articles sur quoi moi après ?</p>


feed_id: http://sametmax.com/?p=3928
title: Pendant ce temps, à Vera Cruz
uri: Pendant-ce-temps-à-Vera-Cruz
url: http://sametmax.com/pendant-ce-temps-chez-sam-et-max/
content:
<pre>[18:48:36 CEST][18:48:36 CEST] Max: mouiiii bonsoir
[18:48:59 CEST] Max: j'ai une petite question de sorting en python
 pour homme poilu intelligent :)
[18:49:12 CEST] Sam: je ne suis pas un homme
[18:49:25 CEST] Max: un surhomme ?
[18:49:33 CEST] Max: un post ado ?
[18:49:38 CEST] Max: un pre-homme
[18:49:46 CEST] Sam: je suis un bot poilu et un intelligent
[18:49:56 CEST] Max: c dur la vie
[18:50:09 CEST] Max: ha sinon t à partir de quand sur [censored]
que je vienne squater pour mes yeux ? :)
[18:53:44 CEST] Sam: mardi je pense
[18:53:46 CEST] Sam: à confirmer
[18:55:13 CEST] Max: ha ok, tu me donneras une fourchette où je
pourrais venir ;o)
[18:55:34 CEST] Sam: tu veux dormir dans une fourchette ?
[18:55:46 CEST] Max: ouais suis devenu indouiste
[18:56:05 CEST] Max: je passe ma troisieme dan de fakir
[18:57:00 CEST] Sam: moi je vais passer à mon troisième verre
de vrai kir
[18:57:03 CEST] Sam: chacun son truc
[19:00:21 CEST] Max: :)
[19:00:29 CEST] Max: in vino veritas
[19:00:35 CEST] Max: c là où tu trouveras la voix
[19:00:45 CEST] Sam: Bonum vinum laetificat cor hominis
[19:01:12 CEST] Max: tu vas pouvoir rentrer dans le cercle très
fermé de cortex
[19:01:23 CEST] Sam: très serré tu veux dire ?
[19:01:38 CEST] Max: esprit mal placé
[19:02:25 CEST] Sam: c'est le kir, ça me déplace les spris
[19:02:47 CEST] Sam: bon c'est quoi ta question python ?
[19:03:11 CEST] Max: ben c bon en fait, je testais en te la posant
parceque je pensais pas que ça marcherait
[19:03:16 CEST] Sam: lol
[19:03:21 CEST] Max: ct pour ordonné sur une clef une liste d'objet
[19:03:28 CEST] Sam: tu vas rire, mon samsung charge plus
[19:03:32 CEST] Max: enfin je pense que ça marche :)
[19:03:41 CEST] Max: quelle camelotte... encore le chargeur ?
[19:03:56 CEST] Sam: sorted(iterable, [key=]) ou iterable.sort() ?
[19:04:04 CEST] Sam: je sais pas, je pleur c'est tout
[19:04:06 CEST] Max: sorted(iterable, [key=])
[19:04:16 CEST] Max: en gros ça donne ça :
[19:04:17 CEST] Max:
related_search = SearchQuerySet()\
                      .filter(content=AutoQuery(related_query),
                              blur_coef__gt=60,
                              duration__gt=300,
                              rating__gt=50)[:500]

sorted(related_search, key=attrgetter('score'),
                                    reverse=True)
[19:04:25 CEST] Sam: parfait
[19:04:34 CEST] Sam: ça mérite une article sur sorted ça
[19:04:42 CEST] Max: le score c un truc retourné par solr,
pas un champs indexé par haystack
[19:04:45 CEST] Sam: le côté "key" est souvent mal compris
[19:04:54 CEST] Max: ouais enfin c bon là à vue de nez ?
[19:05:04 CEST] Max: car moi je pensais que ct sur une liste banale
[19:05:06 CEST] Sam: ouai niquel
[19:05:20 CEST] Sam: tu nous articlise tout ça ?
[19:05:29 CEST] Sam: comment utilise une clé sur "sorted" ?
[19:05:33 CEST] Max: là dans ma liste j'ai des objets search qui
ressemblent à des queryset et dans chaque objet un attribut score
[19:05:39 CEST] Sam: sinon j'ai toujours pas reçu [censored]
 de foxmask
[19:05:46 CEST] Max: pas glop
[19:05:55 CEST] Sam: faudrait peut être regarder le numéro de
livraison sur le site d'UPS
[19:05:59 CEST] Max: je connais que ce cas c un peu con
pour sorted :/
[19:06:21 CEST] Max: je vais pas passer en revue plusieurs cas de
figure ça fera pas un vrai article
[19:06:25 CEST] Sam: y a pas d'order by sur SearchQuerySet pour
 order by score ?
[19:06:42 CEST] Max: ben le order_by se fait sur les champs
 du searchindex
[19:06:48 CEST] Max: pas sur ce que retourne solr
[19:06:52 CEST] Sam: ok
[19:06:56 CEST] Max: là le score est retourné par solr
[19:07:30 CEST] Max: y a un more_like_this sur le
nouveau haystack mais
pas reussi à le faire marcher
[19:07:49 CEST] Max: faudrait lire 1 ou 2 kilometres de
doc en plus
[19:08:41 CEST] Sam: pour sortedy a que ce cas
[19:08:47 CEST] Sam: iterable, et optionellement key
[19:11:38 CEST] Sam: faudrait tentouiller elastic search
un de ces 4
</pre>


feed_id: http://sametmax.com/?p=3953
title: Dis papa, dis papa, dis-moi, dis-moi. Comment c’est fait dans une boucle for ?
uri: Dis-papa-dis-papa-dis-moi-dis-moi-Comment-c-est-fait-dans-une-bo
url: http://sametmax.com/dis-papa-dis-papa-dis-moi-dis-moi-comment-cest-fait-dans-une-boucle-for/
content:
<p>Dis papa, dis papa, dis-moi, dis-moi. Comment c&#8217;est fait dans une boucle <code>for</code> ?</p>
<p>C&#8217;est pas compliquéééééééééééé, j&#8217;vais tout t&#8217;expliquuuuuerrrrrrrrrr.</p>
<p>C´est le p´tit zinzin qui passe par ici:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">class</span> MonIterable<span style="color: black;">&#40;</span><span style="color: #008000;">object</span><span style="color: black;">&#41;</span>: <span style="color: #808080; font-style: italic;"># faisons notre propre itérable</span>
...
...     <span style="color: #ff7700;font-weight:bold;">def</span> <span style="color: #0000cd;">__init__</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>:
...         <span style="color: #008000;">self</span>.<span style="color: black;">values</span> = <span style="color: black;">&#91;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">2</span><span style="color: black;">&#93;</span>
...
...     <span style="color: #ff7700;font-weight:bold;">def</span> <span style="color: #0000cd;">__iter__</span><span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>: <span style="color: #808080; font-style: italic;"># ('for' appelle __iter__ automatiquement)</span>
...         <span style="color: #ff7700;font-weight:bold;">return</span> <span style="color: #008000;">self</span> <span style="color: #808080; font-style: italic;"># __iter__ doit renvoyer un iterateur, ici nous-même</span>
...
...     <span style="color: #ff7700;font-weight:bold;">def</span> next<span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>: <span style="color: #808080; font-style: italic;"># chaque tour de boucle, for appelle next()</span>
...         <span style="color: #ff7700;font-weight:bold;">if</span> <span style="color: #008000;">self</span>.<span style="color: black;">values</span>: <span style="color: #808080; font-style: italic;"># qui retourne une des valeus de self.values</span>
...             <span style="color: #ff7700;font-weight:bold;">return</span> <span style="color: #008000;">self</span>.<span style="color: black;">values</span>.<span style="color: black;">pop</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># en l'enlevant de la liste initiale</span>
...         <span style="color: #ff7700;font-weight:bold;">raise</span> <span style="color: #008000;">StopIteration</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># si il y en a plus, il dit stop !</span>
...</pre></div></div>

<p>Et qui va toucher le p´tit machinnnnnnnnnnnnnnnnnnnnnnnnn !</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> MonIterable<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>: <span style="color: #808080; font-style: italic;"># ceci appelle next() jusqu'à StopIteration</span>
...    <span style="color: #ff7700;font-weight:bold;">print</span> x
<span style="color: #ff4500;">2</span>
<span style="color: #ff4500;">1</span></pre></div></div>

<p>Et le p´tit machin qui repasse par là:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> iterateur = <span style="color: #008000;">iter</span><span style="color: black;">&#40;</span>MonIterable<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># Voilà ce que ça donne à la main</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> iterateur.<span style="color: black;">next</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #ff4500;">2</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> iterateur.<span style="color: black;">next</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #ff4500;">1</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> iterateur.<span style="color: black;">next</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># l'exception: mécanisme naturel de Python pour stopper une boucle !</span>
Traceback <span style="color: black;">&#40;</span>most recent call last<span style="color: black;">&#41;</span>:
  File <span style="color: #483d8b;">&quot;&lt;pyshell#9&gt;&quot;</span>, line <span style="color: #ff4500;">19</span>, <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #66cc66;">&lt;</span>module<span style="color: #66cc66;">&gt;</span>
    iterateur.<span style="color: black;">next</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
  File <span style="color: #483d8b;">&quot;&lt;pyshell#9&gt;&quot;</span>, line <span style="color: #ff4500;">14</span>, <span style="color: #ff7700;font-weight:bold;">in</span> next
    <span style="color: #ff7700;font-weight:bold;">raise</span> <span style="color: #008000;">StopIteration</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #008000;">StopIteration</span></pre></div></div>

<p>Et qui fait marcher ce p´tit zinzinnnnnnnnnnnnn !</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> iterateur = <span style="color: #008000;">iter</span><span style="color: black;">&#40;</span><span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">3</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># c'est pareil pour tous les iterables</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> iterateur.<span style="color: black;">next</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># un iterateur est juste un truc avec une méthode next()</span>
<span style="color: #ff4500;">0</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> iterateur.<span style="color: black;">next</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># next() doit retourner la prochain valeur de l'iterable</span>
<span style="color: #ff4500;">1</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> iterateur.<span style="color: black;">next</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># un itérateur itère donc sur un iterable</span>
<span style="color: #ff4500;">2</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> iterateur.<span style="color: black;">next</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># jusqu'à la fin, où il lève StopIteratino</span>
Traceback <span style="color: black;">&#40;</span>most recent call last<span style="color: black;">&#41;</span>:
  File <span style="color: #483d8b;">&quot;&lt;ipython-input-19-6c9f9efdd35c&gt;&quot;</span>, line <span style="color: #ff4500;">1</span>, <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #66cc66;">&lt;</span>module<span style="color: #66cc66;">&gt;</span>
    iterateur.<span style="color: black;">next</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #008000;">StopIteration</span></pre></div></div>

<p>Ah bon ?</p>


feed_id: http://sametmax.com/?p=3962
title: Sortir de plusieurs boucles for imbriquées en Python
uri: Sortir-de-plusieurs-boucles-for-imbriquées-en-Python
url: http://sametmax.com/sortir-de-plusieurs-boucles-for-imbriquees-en-python/
content:
<p>Le mot clé <code>break</code> permet de sortir d&#8217;une boucle <code>for</code> abruptement. Mais une seule. Parfois on a 3, 4 boucles imbriquées, et on aimerait tellement sortir de toutes d&#8217;un coup.</p>
<p>Ce que je vais vous montrer est mal. Mais c&#8217;est tellement bon.</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #808080; font-style: italic;"># on fait une exception qui hérite de StopIteration car c'est ce qui est utilisé</span>
<span style="color: #808080; font-style: italic;"># de toute façon pour arrêter une boucle</span>
<span style="color: #ff7700;font-weight:bold;">class</span> MultiStopIteration<span style="color: black;">&#40;</span><span style="color: #008000;">StopIteration</span><span style="color: black;">&#41;</span>:
    <span style="color: #808080; font-style: italic;"># la classe est capable de se lever elle même comme exception</span>
    <span style="color: #ff7700;font-weight:bold;">def</span> throw<span style="color: black;">&#40;</span><span style="color: #008000;">self</span><span style="color: black;">&#41;</span>:
        <span style="color: #ff7700;font-weight:bold;">raise</span> <span style="color: #008000;">self</span>
&nbsp;
&nbsp;
@contextmanager
<span style="color: #ff7700;font-weight:bold;">def</span> multibreak<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>:
    <span style="color: #808080; font-style: italic;"># le seul boulot de notre context manager c'est de donne le moyen de lever</span>
    <span style="color: #808080; font-style: italic;"># l'exception tout en l'attrapant</span>
    <span style="color: #ff7700;font-weight:bold;">try</span>:
        <span style="color: #ff7700;font-weight:bold;">yield</span> MultiStopIteration<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>.<span style="color: black;">throw</span>
    <span style="color: #ff7700;font-weight:bold;">except</span> MultiStopIteration:
        <span style="color: #ff7700;font-weight:bold;">pass</span></pre></div></div>

<p>En gros on se créé un petit <a href="http://sametmax.com/les-context-managers-et-le-mot-cle-with-en-python/">context manager</a>, dont le seul but est de créer une exception qui va remonter en pêtant toutes les boucles. Je vous avais dit que c&#8217;était mal</p>
<p>Ca s&#8217;utilise comme ça:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">with</span> multibreak<span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #ff7700;font-weight:bold;">as</span> stop:
...     <span style="color: #ff7700;font-weight:bold;">for</span> x <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">4</span><span style="color: black;">&#41;</span>:
...         <span style="color: #ff7700;font-weight:bold;">for</span> z <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">4</span><span style="color: black;">&#41;</span>:
...             <span style="color: #ff7700;font-weight:bold;">for</span> w <span style="color: #ff7700;font-weight:bold;">in</span> <span style="color: #008000;">range</span><span style="color: black;">&#40;</span><span style="color: #ff4500;">1</span>, <span style="color: #ff4500;">4</span><span style="color: black;">&#41;</span>:
...                 <span style="color: #ff7700;font-weight:bold;">print</span> w
...                 <span style="color: #ff7700;font-weight:bold;">if</span> x <span style="color: #66cc66;">*</span> z <span style="color: #66cc66;">*</span> w == <span style="color: #ff4500;">2</span> <span style="color: #66cc66;">*</span> <span style="color: #ff4500;">2</span> <span style="color: #66cc66;">*</span> <span style="color: #ff4500;">2</span>:
...                     <span style="color: #ff7700;font-weight:bold;">print</span> <span style="color: #483d8b;">'stop'</span>
...                     <span style="color: black;">stop</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># appel MultiStopIteration().throw()</span>
...
<span style="color: #ff4500;">1</span>
<span style="color: #ff4500;">2</span>
<span style="color: #ff4500;">3</span>
<span style="color: #ff4500;">1</span>
<span style="color: #ff4500;">2</span>
<span style="color: #ff4500;">3</span>
<span style="color: #ff4500;">1</span>
<span style="color: #ff4500;">2</span>
<span style="color: #ff4500;">3</span>
<span style="color: #ff4500;">1</span>
<span style="color: #ff4500;">2</span>
<span style="color: #ff4500;">3</span>
<span style="color: #ff4500;">1</span>
<span style="color: #ff4500;">2</span>
stop</pre></div></div>

<p>Je vous avais dit que ça serait bon.</p>
<p>A part le fait que ce n&#8217;est pas très rapide au moment du bubbling de l&#8217;exception sur 3 blocks, il n&#8217;y a aucun danger ou side-effect. On triche en fait à peine, car <a href="http://sametmax.com/dis-papa-dis-papa-dis-moi-dis-moi-comment-cest-fait-dans-une-boucle-for/">le mécanisme interne des boucles en Python utilise de toute façon déjà une exception</a> (StopIteration) pour dire à une boucle quand s&#8217;arrêter.</p>
<p>Bref, encore une victoire de connard.</p>


feed_id: http://sametmax.com/?p=3979
title: La fonction anonyme appelée immédiatement en Javascript: (function())()
uri: La-fonction-anonyme-appelée-immédiatement-en-Javascript-(function()
url: http://sametmax.com/la-fonction-anonyme-appelee-immediatement-en-javascript-function/
content:
<p>Javascript est un langage qui a plein d&#8217;idiomes bien à lui. En effet, c&#8217;est un langage très puissant, et ausi plein de couilles velues planquées ici et là. Les ninjas JS ont donc créée des astuces pour pallier à ces problèmes, en utilisant la force de leur outil.</p>
<p>Un des gros soucis en JS, c&#8217;est qu&#8217;il dépend beaucoup des variables globales, qui sont une grosse source d&#8217;ennuis en tout genre. Et il est très facile de déclarer ou d&#8217;utiliser une variable globale par erreur.</p>
<p>Pour limiter ce problème, on utilise la technique de la <a href="http://sametmax.com/fonctions-anonymes-en-python-ou-lambda/">fonction anonyme</a> immédiatement appelée. Cela fonctionne comme ceci, au lieu de faire:<br />
pre lang=&#8221;javascript&#8221;><br />
    alert(&#8216;rouge&#8217;);
</pre>
<p>On fait:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'rouge'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<h2>Explication pas à pas</h2>
<p>En effet, en Javascript on peut créer une fonction sans lui donner de nom. C'est ce qu'on appelle une fonction anonyme:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'rouge'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span></pre></div></div>

<p>On peut attribuer cette fonction à une variable.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #003366; font-weight: bold;">var</span> une_variable_qui_passait_par_la <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'rouge'</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span></pre></div></div>

<p>Et derrière on peut appeler la fonction ainsi:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">une_variable_qui_passait_par_la<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>Mais dans notre cas, on ne met pas la fonction dans une variable, on l'enferme dans des parenthèses, ce qui garde la référence le temps de l'appeler, et on l'appelle. On fait la même chose que précédement en fait, on saute juste une étape :</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span> <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'rouge'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span><span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>La référence à la fonction est perdue, on ne pourra pas l'appeler de nouveau. Mais on s'en branle fortement, on voulait juste l'appeler une fois de toute façon.</p>
<p>Pour rendre le code plus lisible, on le met sur plusieurs lignes:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'rouge'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #006600; font-style: italic;">/* on éxécute la fonction cash pistache */</span></pre></div></div>

<p>Maintenant pour comprendre ce que ça fait, il faut juste réaliser que le bout de code ci-dessous fait EXACTEMENT la même chose que le bout de code juste au dessus :</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'route'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span></pre></div></div>

<p>Car on déclare la fonction, mais on l'éxécute tout de suite. Donc dans les deux cas, au chargement du script, un aura une alerte immédiatement.</p>
<h2>Mais putain si ça fait la même chose, pourquoi tu nous gonfles avec ça ?</h2>
<p>Parceque dans le cas du dessus ça fait la même chose, mais ça a des propriétés en plus. Vous vous doutez bien qu'on tape pas 4 lignes en trop pour le plaisir (à part en Java).</p>
<p>En effet, en créant une fonction, on crée un scope. Ainsi, tout ce qui est déclaré avec <code>var</code> dans la fonction sera garanti de ne pas être une variable globale. Pas d'effet de bord sur le monde extérieur. Et le monde extérieur n'a PAS accès aux variables déclarées dans la fonction. Par contre la fonction a accès aux variables globales !</p>
<p>Par exemple, dans un navigateur, vous avez toujours accès à l'objet <code>window</code> et l'objet <code>Date</code> partout dans le code.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">/*
    Ici vous avez accès à window et Date
*/</span>
&nbsp;
<span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
&nbsp;
    <span style="color: #006600; font-style: italic;">/* Ceci ne va pas changer l'objet window en dehors de la fonction
        car on redéclare la variable, à l'intérieur du scope de la fonction.
     */</span>
    <span style="color: #003366; font-weight: bold;">var</span> window <span style="color: #339933;">=</span> <span style="color: #3366CC;">'3.1'</span><span style="color: #339933;">;</span>
&nbsp;
    <span style="color: #003366; font-weight: bold;">var</span> rideau <span style="color: #339933;">=</span> <span style="color: #3366CC;">'vista'</span><span style="color: #339933;">;</span>
&nbsp;
    <span style="color: #009966; font-style: italic;">/* Ici vous avez accès à Date */</span>
&nbsp;
    <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">new</span> Date<span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span>
&nbsp;
&nbsp;
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
&nbsp;
<span style="color: #006600; font-style: italic;">/*
    Ici vous n'avez PAS accès à &quot;rideau&quot;
*/</span></pre></div></div>

<p>Il est donc une bonne pratique de mettre TOUT son script dans une fonction qui s'auto-appelle, pour l'isoler du monde exterieur et ne pas pourrir le namespace global. Si on avait pas fait ça, et qu'un autre script définissait aussi <code>rideau</code>, l'un des deux aurait écrasé l'autre. Et dans tous les cas on aurait écrasé <code>window</code>.</p>
<h2>Encore mieux</h2>
<p>Comme on crée un conteneur isolé, on peut faire ce que l'on veut dedans. Et on a deux moyens de communique avec ce conteneur. D'abord, les variables globales. Ensuite, les paramètres de la fonction auto-appelée.</p>
<p>On peut exposer le contenu de la fonction à travers les variables globales. Par exemple, vous faites un générateur de 'pouet', chose importante s'il en est :</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
&nbsp;
    <span style="color: #009966; font-style: italic;">/* ces variables ne sont pas accessibles depuis l'extérieur */</span>
    <span style="color: #003366; font-weight: bold;">var</span> pouetGenerator <span style="color: #339933;">=</span> <span style="color: #009900;">&#123;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
    <span style="color: #003366; font-weight: bold;">var</span> variablePrivee <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">;</span>
&nbsp;
    <span style="color: #009966; font-style: italic;">/* ces fonctions sont accessibles seulement depuis pouetGenerator */</span>
    pouetGenerator.<span style="color: #660066;">fairePouet</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
        <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'pouet'</span><span style="color: #009900;">&#41;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    pouetGenerator.<span style="color: #660066;">nePasFairePouet</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
        <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>variablePrivee<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'pas pouet'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #009966; font-style: italic;">/* On rend notre pouetGenerator accessible au reste du monde */</span>
    window.<span style="color: #660066;">pouetGenerator</span> <span style="color: #339933;">=</span> pouetGenerator<span style="color: #339933;">;</span>
&nbsp;
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span>
&nbsp;
<span style="color: #009966; font-style: italic;">/* On peut utiliser notre générateur de pouet partout ailleurs */</span>
pouetGenerator.<span style="color: #660066;">nePasFairePouet</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>En effet, tout ce qui est attaché à <code>window</code> devient une variable globale dans un navigateur. C'est une caractéristique de Javascript dans un navigateur Web: <code>window</code> est un objet accessible partout, et on a accès partout à ses attributs. On a donc notre code parfaitement isolé (la seule chose exposée c'est notre point d'entrée : <code>pouetGenerator</code>). On ne pollue pas le namespace. En prime personne n'a accès aux variables privées comme <code>variablePrivee</code>;</p>
<p>On peut aussi utiliser les paramètres et les valeurs de retour pour cela :</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #006600; font-style: italic;">/* pouetGenerator, déclaré sans &quot;var&quot;, est une variable globale */</span>
pouetGenerator <span style="color: #339933;">=</span> <span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>chaine_du_pouet<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
&nbsp;
    <span style="color: #009966; font-style: italic;">/* ces variables ne sont pas accessibles depuis l'extérieur */</span>
    <span style="color: #003366; font-weight: bold;">var</span> pouetGenerator <span style="color: #339933;">=</span> <span style="color: #009900;">&#123;</span><span style="color: #009900;">&#125;</span><span style="color: #339933;">;</span>
    <span style="color: #003366; font-weight: bold;">var</span> variablePrivee <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">true</span><span style="color: #339933;">;</span>
&nbsp;
    <span style="color: #009966; font-style: italic;">/* ces fonctions sont accessibles seulement depuis pouetGenerator */</span>
    pouetGenerator.<span style="color: #660066;">fairePouet</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
        <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span>chaine_du_pouet<span style="color: #009900;">&#41;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    pouetGenerator.<span style="color: #660066;">nePasFairePouet</span> <span style="color: #339933;">=</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
        <span style="color: #000066; font-weight: bold;">if</span> <span style="color: #009900;">&#40;</span>variablePrivee<span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
            <span style="color: #000066;">alert</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'pas pouet'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
        <span style="color: #009900;">&#125;</span>
    <span style="color: #009900;">&#125;</span>
&nbsp;
    <span style="color: #006600; font-style: italic;">/* On rend notre pouetGenerator accessible au reste du monde
        en la retournant, ce qui va mettre la référence dans le pouetGenerator
        qui est la variable globale.
    */</span>
    <span style="color: #000066; font-weight: bold;">return</span> pouetGenerator<span style="color: #339933;">;</span>
&nbsp;
<span style="color: #009966; font-style: italic;">/* On passe 'pouet' en paramètre, il va se retrouver dans chaine_du_pouet */</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'pouet'</span><span style="color: #009900;">&#41;</span>
&nbsp;
<span style="color: #009966; font-style: italic;">/* On peut utiliser notre générateur de pouet au même niveau */</span>
pouetGenerator.<span style="color: #660066;">nePasFairePouet</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>Il y a deux différences dans ce code. La première, c'est qu'on met la variable à disposition en la retournant plutôt qu'en l'attachant à <code>document</code>. La seconde, c'est qu'on passe <code>'pouet'</code>.</p>
<p>On pourrait se dire que l'interêt est limité, mais considérez l'exempe suivant:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>$<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
    $<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'p'</span><span style="color: #009900;">&#41;</span>.<span style="color: #660066;">css</span><span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'color'</span><span style="color: #339933;">,</span> <span style="color: #3366CC;">'rouge-fluo'</span><span style="color: #009900;">&#41;</span>
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span>jQuery.<span style="color: #660066;">noConflic</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p><code>jQuery.noConflic()</code> restaure <code>$</code> à sa valeur précédente, permettant à d'autres libs d'utiliser <code>$</code> (comme la lib <em>prototype.js</em>). Mais <code>jQuery.noConflic()</code> retourne aussi l'objet <code>jQuery</code>, que l'on passe en paramètre. Ce paramètre est nommé <code>$</code> dans la signature de la fonction. Dans notre fonction, on peut donc QUAND MÊME utiliser <code>$</code> pour faire référence à <code>jQuery</code> car tout ce qui est dans la fonction est isolée du reste du monde. Et le reste du monde peut utiliser <code>$</code> pour autre chose que <code>jQuery</code>.</p>
<h2>Best practice</h2>
<p>Généralement un code de production pour un script complet ressemble donc à ça:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;"><span style="color: #339933;">;</span><span style="color: #009900;">&#40;</span><span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span>alias<span style="color: #009900;">&#41;</span><span style="color: #009900;">&#123;</span>
<span style="color: #3366CC;">&quot;use strict&quot;</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #009966; font-style: italic;">/* tout le code du script va ici */</span>
&nbsp;
<span style="color: #003366; font-weight: bold;">var</span> une_variable_privee<span style="color: #339933;">;</span>
&nbsp;
window.<span style="color: #660066;">une_variable_exposee</span> <span style="color: #339933;">=</span> <span style="color: #3366CC;">'foo'</span><span style="color: #339933;">;</span>
&nbsp;
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span><span style="color: #009900;">&#40;</span>truc_a_aliaser<span style="color: #009900;">&#41;</span></pre></div></div>

<p>Notez le <code>;</code> au début qui permet de rajouter votre script à la suite d'un autre script même si celui-ci a  oublié de mettre un <code>;</code> sur sa dernière ligne (utile pour les minifieurs).</p>
<p>Notez aussi le <code>"use strict";</code> qui dit au navigateur que tout ce qui se trouve dans cette fonction devra être traité par un parseur strict qui vous signalera plus d'erreurs de code. Cela ne s'applique qu'à la fonction, laissant le reste du monde le droit d'utiliser du code moins strict.</p>


feed_id: http://sametmax.com/?p=3977
title: Include / require / import en javascript
uri: Include-require-import-en-javascript
url: http://sametmax.com/include-require-import-en-javascript/
content:
<p>On ne peut pas inclure un script dans un script en JS dans un navigateur Web. Il n&#8217;y a pas de mot clé <code>import</code>, <code>include</code> ou <code>require</code>.</p>
<p>On peut néanmoins trouver un moyen d&#8217;inclure du code en le téléchargeant et en l&#8217;incluant dans la page.</p>
<h2>Solution 1, la bourrine</h2>
<p>On peut faire une requête GET et un <code>eval sur</code>. C&#8217;est dangereux. C&#8217;est bancal. Ca marche que pour le domaine en cours. C&#8217;est pas une bonne idée. Je ne vous le montre donc pas.</p>
<h2>Solution 2, la maline</h2>
<p>On va créer une balise <code>&lt;script&gt;&lt;/script&gt;</code> et la faire pointer sur le fichier à télécharger. Ainsi on utilise le mécanisme naturel pour le navigateur d&#8217;include du code.</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">var include = function(url, callback){
&nbsp;
    /* on crée une balise<span style="color: #339933;">&lt;</span>script type<span style="color: #339933;">=</span><span style="color: #3366CC;">&quot;text/javascript&quot;</span><span style="color: #339933;">&gt;&lt;/</span>script<span style="color: #339933;">&gt;</span> */
    var script = document.createElement('script');
    script.type = 'text/javascript';
&nbsp;
    /* On fait pointer la balise sur le script qu'on veut charger
       avec en prime un timestamp pour éviter les problèmes de cache
    */
&nbsp;
    script.src = url + '?' + (new Date().getTime());
&nbsp;
    /* On dit d'exécuter cette fonction une fois que le script est chargé */
    if (callback) {
        script.onreadystatechange = callback;
        script.onload = script.onreadystatechange;
    }
&nbsp;
    /* On rajoute la balise script dans le head, ce qui démarre le téléchargement */
    document.getElementsByTagName('head')[0].appendChild(script);
}</pre></div></div>

<p>Ca s&#8217;utilise comme ça:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">include<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'http://adressedemonscript.com/fichier.js'</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    code à exécuter une fois que le script est chargé
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span></pre></div></div>

<p>La partie <a href="http://sametmax.com/quest-ce-quun-callback/">callback</a> est très importante. En effet, si vous essayez d&#8217;exécuter du code <strong>après</strong> <code>include()</code> qui dépend du code chargé <strong>par</strong> <code>include()</code>, ça va foirer : le code n&#8217;est pas encore téléchargé. En effet, les navigateurs téléchargent les balises scripts en arrière plan et en parallèle :</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">include<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'http://adressedemonscript.com/fichier.js'</span><span style="color: #009900;">&#41;</span><span style="color: #339933;">;</span>
code à exécyter une fois que le script est chargé</pre></div></div>

<p>Il faut donc mettre ce code dans un callback, pour garantir qu&#8217;il soit lancé quand le script a terminé de chargé.</p>
<h2>Solution 3, la coquine</h2>
<p>jQuery, encore et toujours, possède un raccourcis pour faire tout ça pour vous:</p>

<div class="wp_syntax"><div class="code"><pre class="javascript" style="font-family:monospace;">$<span style="color: #009900;">&#40;</span><span style="color: #3366CC;">'http://adressedemonscript.com/fichier.js'</span><span style="color: #339933;">,</span> <span style="color: #003366; font-weight: bold;">function</span><span style="color: #009900;">&#40;</span><span style="color: #009900;">&#41;</span> <span style="color: #009900;">&#123;</span>
    code à exécuter une fois que le script est chargé
<span style="color: #009900;">&#125;</span><span style="color: #009900;">&#41;</span></pre></div></div>


feed_id: http://sametmax.com/?p=3956
title: Firefox n’affiche plus les styles CSS ni les images
uri: Firefox-n-affiche-plus-les-styles-CSS-ni-les-images
url: http://sametmax.com/firefox-naffiche-plus-les-styles-css-ni-les-images/
content:
<p>Après avoir vidé le cache, il peut arriver que notre panda roux n&#8217;affiche plus les styles CSS ou les images: il n&#8217;y a plus aucune mise en page, juste du texte noir sur une page blanche. Damned !</p>
<p>La solution est de forcer le refresh de la page et du cache avec <code>Ctrl + Shift + R</code>.</p>


feed_id: http://sametmax.com/?p=4004
title: Bonne année 2013 avec GoGole !
uri: Bonne-année-2013-avec-GoGole
url: http://sametmax.com/bonne-annee-2013-avec-gogole/
content:
<p>Ce matin en cherchant un numéro de téléphone sur Google je tombe sur leur fameuse suggestion à droite, le joli encoart proposant une photo de l&#8217;adresse + un bout de Google Map. Comme d&#8217;habitude je clique dessus pour avoir un peu plus de renseignements.</p>
<p>Et là ho surprise étant loggué avec un compte spécial &#8220;pseudo batard parceque je veux pas que mon nom traine partout&#8221; je me fait tirer les oreilles par Google car en cliquant sur plus d&#8217;infos je suis arrivé sur la page Google+.</p>
<blockquote><p>
Votre profil est suspendu le temps de l&#8217;examen</p>
<p>Nous examinons actuellement votre profil pour déterminer s&#8217;il respecte le Règlement relatif aux noms et les Règlements relatifs au contenu et au comportement de l&#8217;utilisateur de Google+. En règle générale, cette procédure ne prend que quelques jours.</p>
<p>Pendant ce temps, vous ne pourrez pas utiliser certains services Google qui nécessitent un profil actif, notamment Google+, Reader et Picasa. Vous pourrez en revanche continuer d&#8217;utiliser les autres produits Google, par exemple Gmail.</p>
<p>Si votre profil est accepté, il sera accessible dans les conditions normales. S&#8217;il ne l&#8217;est pas, vous serez informé par e-mail de notre refus et la suspension de votre profil sera maintenue. Dans ce cas, vous aurez la possibilité de modifier de nouveau le profil ou le nom avant de demander un nouvel examen.</p>
<p>Nous vous prions de nous excuser des désagréments occasionnés.</p></blockquote>
<p>Ca m&#8217;a fait penser à ce pays en Asie qui veut mettre un nom sur chaque pseudo&#8230;Vous savez la Corée , je n&#8217;ai plus la news, si quelqu&#8217;un la retrouve&#8230;</p>
<p>Je sais que depuis quelques temps Google+ essayait de faire utiliser <a href="http://www.numerama.com/magazine/23250-google-pousse-a-utiliser-son-vrai-nom-sur-youtube.html">son vrai nom</a> mais de là à désactiver même partiellement un compte&#8230;</p>
<p>Bref comme pas mal de personnes je vais commencer doucement à aller voir ce qui se passe ailleurs pour le reste de leurs services.</p>
<p><a href="http://sametmax.com/quitter-google-recherche-email-et-chat/" title="Quitter Google : recherche, email et chat">Et Je vais surement suivre les conseils d&#8217;oncle Sam :)</a></p>
<p>Bon sur ce je vous souhaite à tous une bonne année 2013, gardez vous du malin.</p>


feed_id: http://sametmax.com/?p=3499
title: Le merdier du “stacking context” en CSS (aka “pourquoi mon z-index marche pas bordel de merde” ?)
uri: Le-merdier-du-stacking-context-en-CSS-(aka-pourquoi-mon-z-ind
url:
http://sametmax.com/le-merdier-du-stacking-context-en-css-aka-pourquoi-mon-z-index-marche-pas-bordel-de-merde/

content:
<p>C&#8217;est une règle en CSS que beaucoup de designers connaissent, mais la première fois qu&#8217;on s&#8217;y frotte on se sent très con: on ne peut pas appliquer <code>z-index</code> à un élément dont le parent possède déjà un &#8220;stacking context&#8221;.</p>
<p>Ce n&#8217;est pas un bug, c&#8217;est comme ça que c&#8217;est supposé fonctionner.</p>
<h2>Qu&#8217;est-ce qu&#8217;un &#8220;stacking context&#8221; ?</h2>
<p>On appelle &#8220;stacking context&#8221; l&#8217;état d&#8217;un élément que le navigateur garde en mémoire pour effectuer le rendu de cet élément dans la page. Le &#8220;stacking context&#8221; dit si l&#8217;élément doit être devant ou derrière chaque <strong>autre</strong> élément se superposant à l&#8217;écran avec lui.</p>
<p>Chaque fois que vous utilisez une propriété comme <code>z-index</code>, <code>opacity</code> ou <code>transform</code> sur un élément dans un fichier CSS, le navigateur recalcule le &#8220;stacking context&#8221; pour savoir si il met maintenant cet élément devant ou derrière les autres à la même position que lui.</p>
<h2>Et du coup, j&#8217;ai pas compris le début, c&#8217;est quoi déjà le problème ?</h2>
<p>Si vous faites un truc qui change le &#8220;stacking context&#8221; d&#8217;un élément, vous ne pouvez appliquer <code>z-index</code> sur aucun de ses enfants. </p>
<p>Ainsi si vous avez un HTML comme ça:</p>

<div class="wp_syntax"><div class="code"><pre class="html" style="font-family:monospace;">&lt;p class=&quot;parent&quot;&gt;
    &lt;span class=&quot;child&quot;&gt;Truc&lt;/span&gt;
&lt;/p&gt;</pre></div></div>

<p>Et que vous faites ça dans votre CSS:</p>

<div class="wp_syntax"><div class="code"><pre class="css" style="font-family:monospace;"><span style="color: #6666ff;">.parent</span> <span style="color: #00AA00;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">z-index</span><span style="color: #00AA00;">:</span> <span style="color: #cc66cc;">1</span><span style="color: #00AA00;">;</span>
    opacity<span style="color: #00AA00;">:</span> <span style="color: #cc66cc;">0.5</span><span style="color: #00AA00;">;</span>
    transform<span style="color: #00AA00;">:</span> rotate<span style="color: #00AA00;">&#40;</span>5deg<span style="color: #00AA00;">&#41;</span><span style="color: #00AA00;">;</span>
<span style="color: #00AA00;">&#125;</span>
&nbsp;
<span style="color: #6666ff;">.child</span> <span style="color: #00AA00;">&#123;</span>
    <span style="color: #000000; font-weight: bold;">z-index</span><span style="color: #00AA00;">:</span> -<span style="color: #cc66cc;">1</span><span style="color: #00AA00;">;</span>
<span style="color: #00AA00;">&#125;</span></pre></div></div>

<p>La dernière règle n&#8217;aura aucun effet. </p>
<p>Donc si vous vous acharnez sur F5 parce qu&#8217;un <code>z-index</code> semble ne pas marcher quelque part, vous savez maintenant qu&#8217;il faut juste remonter la chaîne de tous les parents de cet élément pour voir si vous avez pas à un moment changé le &#8220;stacking context&#8221; de l&#8217;un d&#8217;entre eux.</p>


feed_id: http://sametmax.com/?p=4029
title: Évolution de la courbe d’apprentissage d’un dev front end
uri: Évolution-de-la-courbe-d-apprentissage-d-un-dev-front-end
url: http://sametmax.com/evolution-de-la-courbe-dapprentissage-dun-dev-front-end/
content:
<!-- iframe plugin v:2.3 - wordpress.org/extend/plugins/iframe/ -->
<iframe src="http://fr.slideshare.net/slideshow/embed_code/15885873" width="427" height="356" frameborder="0" marginwidth="0" marginheight="0" scrolling="no" style="border:1px solid #CCC;border-width:1px 1px 0;margin-bottom:5px" 1="webkitallowfullscreen" 2="mozallowfullscreen" class="iframe-class"></iframe>


feed_id: http://sametmax.com/?p=4036
title: Path.py plus en détail
uri: Path-py-plus-en-détail
url: http://sametmax.com/path-py-plus-en-detail/
content:
<p>La première fois que j&#8217;avais rencontré <code>path.py</code>, je l&#8217;avais trouvé &#8220;juste pratique&#8221;, et donc je n&#8217;avais pas passé plus de temps dessus. Un jour je me suis poussé à l&#8217;utiliser partout dans un projet type &#8220;labo&#8221; dans lequel je mettais plein de libs à l&#8217;épreuve du feu. Force est de constater que sur le long terme, cette bibliothèque fait gagner beaucoup à un projet pour un coût infime. Je l&#8217;inclus maintenant par défaut partout.</p>
<h2>A quoi sert path.py ?</h2>
<p><em>path.py</em> est typiquement une lib qui ne sert à rien à première vue, car il n&#8217;y a rien qu&#8217;on puisse faire avec qu&#8217;on ne puisse déjà faire avec la lib standard de Python. C&#8217;est juste un wrapper autour de <code>os</code>, <code>os.path</code> et <code>shutils</code>. Un peu comme <a href="http://docs.python-requests.org/en/latest/index.html">requests</a> pour <code>urllib</code> en fait.</p>
<p>Elle permet juste de manipuler les fichiers, et chemin de fichiers. C&#8217;est tout.</p>
<h2>Quel interêt alors ?</h2>
<p>L&#8217;API est propre, cohérente, simple, intuitive. En un mot, c&#8217;est beau. On gagne du temps à l&#8217;usage, à la relecture et au debugging, car le code est devenu tout petit et tellement facile à comprendre. Mais le plus fort, c&#8217;est que le coût de transition est quasi nul: tout code utilisant <em>path.py</em> est par défault compatible avec le code précédent, sans changer une virgule.</p>
<h2>Montre moi</h2>
<p><code>&lt;music&gt;Lunatic Calm - Leave You Far Behind&lt;/music&gt;</code></p>
<p>Installation (ceci dit <a href="https://github.com/jaraco/path.py/blob/master/path.py">ça tient dans un fichier</a>&#8230;)</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;">pip install path.<span style="color: black;">py</span></pre></div></div>

<p>On importe, et on créer un objet <code>path</code> à partir d&#8217;une chaîne de caractère représentant un chemin de fichier ou de dossier :</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">from</span> path <span style="color: #ff7700;font-weight:bold;">import</span> path
<span style="color: #66cc66;">&gt;&gt;&gt;</span> tmp = path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/'</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Manipuler un chemin de fichier n&#8217;a jamais été aussi facile</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span> = tmp / <span style="color: #483d8b;">'new.txt'</span> <span style="color: #808080; font-style: italic;"># &quot;/&quot; fait os.path.join()</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>
path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/new.txt'</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">isfile</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #008000;">False</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">touch</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># créer le fichier vide</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">isfile</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #008000;">True</span></pre></div></div>

<p>Extraire des données également:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">ext</span>
<span style="color: #483d8b;">'.txt'</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">name</span>
path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'new.txt'</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">parent</span>
path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp'</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">parent</span>.<span style="color: black;">parent</span>
path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/'</span><span style="color: black;">&#41;</span></pre></div></div>

<p>C&#8217;est joli. On en mangerait. Notez que chaque méthode retourne un nouvel objet <code>path()</code> sur lequel on peut donc appliquer les mêmes méthodes.</p>
<p>En prime, un objet <code>path()</code> se comporte aussi comme une string:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">print</span> <span style="color: #dc143c;">new</span>
/tmp/<span style="color: #dc143c;">new</span>.<span style="color: black;">txt</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">upper</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #483d8b;">'/TMP/NEW.TXT'</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">os</span>.<span style="color: black;">path</span>.<span style="color: black;">join</span><span style="color: black;">&#40;</span><span style="color: #dc143c;">new</span>.<span style="color: black;">parent</span>, <span style="color: #483d8b;">'new_new.txt'</span><span style="color: black;">&#41;</span>
path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/new_new.txt'</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Du coup, aucun problème de migration de l&#8217;ancien code. Utiliser <code>path.py</code> n&#8217;a virtuellement que le coût de l&#8217;install et de l&#8217;import.</p>
<p>On a aussi accès à tout un tas de méthodes avancées:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> tmp.<span style="color: black;">dirs</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># listing du dossier courant</span>
<span style="color: black;">&#91;</span>path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/pulse-XnVNgklabjGI'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/ssh-vrCzN4692eCp'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/pulse-PKdhtXMmr18n'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/.truecrypt_aux_mnt1'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/.X11-unix'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/.ICE-unix'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/plugtmp'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/pulse-2L9K88eMlGn7'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/orbit-sam'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/.winbindd'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/tracker-sam'</span><span style="color: black;">&#41;</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> tmp.<span style="color: black;">files</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: black;">&#91;</span>path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/new.txt'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/backup_tem.zip'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/qtsingleapp-mediat-134e-3e8-lockfile'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/unity_support_test.0'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/apprentissage-130107043807-phpapp02.odp'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/nIzDHlLoho'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/.X0-lock'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/IDcRs0LUki'</span><span style="color: black;">&#41;</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> tmp.<span style="color: black;">files</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'*.txt'</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># filtres</span>
<span style="color: black;">&#91;</span>path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/tmp/new.txt'</span><span style="color: black;">&#41;</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> tmp.<span style="color: black;">walk</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># walk, walkfiles et walkdirs == même chose, récursivement</span>
<span style="color: #66cc66;">&lt;</span>generator <span style="color: #008000;">object</span> walk at 0x2e17960<span style="color: #66cc66;">&gt;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #008000;">list</span><span style="color: black;">&#40;</span>path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/etc/php5'</span><span style="color: black;">&#41;</span>.<span style="color: black;">walkfiles</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">'*.ini'</span><span style="color: black;">&#41;</span><span style="color: black;">&#41;</span>
<span style="color: black;">&#91;</span>path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/etc/php5/conf.d/10-pdo.ini'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/etc/php5/mods-available/pdo.ini'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/etc/php5/cli/php.ini'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/etc/php5/cli/conf.d/10-pdo.ini'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/etc/php5/apache2/php.ini'</span><span style="color: black;">&#41;</span>, path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/etc/php5/apache2/conf.d/10-pdo.ini'</span><span style="color: black;">&#41;</span><span style="color: black;">&#93;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: black;">&#40;</span>tmp / <span style="color: #483d8b;">'test/test/test'</span><span style="color: black;">&#41;</span>.<span style="color: black;">makedirs</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># création récursive</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: black;">&#40;</span>tmp / <span style="color: #483d8b;">'test/test/test'</span><span style="color: black;">&#41;</span>.<span style="color: black;">isdir</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #008000;">True</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: black;">&#40;</span>tmp / <span style="color: #483d8b;">'test/test/test'</span><span style="color: black;">&#41;</span>.<span style="color: black;">makedirs_p</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span> <span style="color: #808080; font-style: italic;"># les &quot;_p&quot; ignorent certaines erreurs</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: black;">&#40;</span>tmp / <span style="color: #483d8b;">'test/test/test'</span><span style="color: black;">&#41;</span>.<span style="color: black;">removedirs</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span></pre></div></div>

<p>Et quelques goodies:</p>

<div class="wp_syntax"><div class="code"><pre class="python" style="font-family:monospace;"><span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #ff7700;font-weight:bold;">with</span> path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'./Work'</span><span style="color: black;">&#41;</span>:
    <span style="color: #ff7700;font-weight:bold;">print</span> path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'.'</span><span style="color: black;">&#41;</span>.<span style="color: black;">realpath</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
    <span style="color: #ff7700;font-weight:bold;">print</span> path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'.'</span><span style="color: black;">&#41;</span>.<span style="color: black;">listdir</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span><span style="color: black;">&#91;</span><span style="color: #ff4500;">0</span><span style="color: black;">&#93;</span>
...     
/home/sam/Work
./A référencer
<span style="color: #66cc66;">&gt;&gt;&gt;</span> path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'~'</span><span style="color: black;">&#41;</span>.<span style="color: black;">expanduser</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/home/sam'</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> path<span style="color: black;">&#40;</span><span style="color: #483d8b;">'/etc/fstab'</span><span style="color: black;">&#41;</span>.<span style="color: #008000;">open</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>.<span style="color: #dc143c;">readline</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #483d8b;">'# /etc/fstab: static file system information.<span style="color: #000099; font-weight: bold;">\n</span>'</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">write_text</span><span style="color: black;">&#40;</span><span style="color: #483d8b;">&quot;BAM d'un coup&quot;</span><span style="color: black;">&#41;</span>
<span style="color: #66cc66;">&gt;&gt;&gt;</span> <span style="color: #dc143c;">new</span>.<span style="color: black;">text</span><span style="color: black;">&#40;</span><span style="color: black;">&#41;</span>
<span style="color: #483d8b;">&quot;BAM d'un coup&quot;</span></pre></div></div>

<p>Très pratique dans un shell.</p>


feed_id: http://sametmax.com/?p=4046
title: ça va trancher chérie
uri: ça-va-trancher-chérie
url: http://sametmax.com/ca-va-trancher-cherie/
content:
<p>on va bouger le site de serveur dans les jours qui viennent alors attendez-vous à voir des trucs disparaitre parce que je vais faire ça comme un gros porc ;)</p>


feed_id: http://sametmax.com/?p=4050
title: Migrer wordpress d’un serveur à un autre – Pense-bête
uri: Migrer-wordpress-d-un-serveur-à-un-autre-Pense-bête
url: http://sametmax.com/migrer-wordpress-dun-serveur-a-un-autre-pense-bete/
content:
<p>Si on veut changer de serveur sans se taper la réinstall de wordpress ça peut devenir casse-tête si on oublie deux trois trucs&#8230;</p>
<p>Voici un petit pense-bête avec pour exemple une config Nginx / WordPress / php5-cgi  sur Ubuntu.</p>
<p>serveura.com = serveur sur lequel se trouve l&#8217;ancien WordPress à migrer<br />
serveurb.com = nouveau serveur qui va accueillir WordPress</p>
<p><strong>1. on sauve la db et on l&#8217;upload sur le nouveau serveur (on peut le faire à la fin si le blog a pas mal d&#8217;activité)</strong><br />
Sur le serveur A:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">mysqldump <span style="color: #660033;">-u</span> user_toto -ppass_toto base_a_toto <span style="color: #000000; font-weight: bold;">&gt;</span> <span style="color: #000000; font-weight: bold;">/</span>tmp<span style="color: #000000; font-weight: bold;">/</span>base_a_toto.sql
rsync <span style="color: #660033;">-P</span> <span style="color: #660033;">-azc</span> <span style="color: #000000; font-weight: bold;">/</span>tmp<span style="color: #000000; font-weight: bold;">/</span>base_a_toto.sql user<span style="color: #000000; font-weight: bold;">@</span>serveurb.com:<span style="color: #000000; font-weight: bold;">/</span>tmp<span style="color: #000000; font-weight: bold;">/</span>base_a_toto.sql</pre></div></div>

<p><strong>2. On copie wordpress sur le nouveau serveur</strong><br />
Sur le serveur A:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">rsync <span style="color: #660033;">-P</span> <span style="color: #660033;">-azc</span> <span style="color: #000000; font-weight: bold;">/</span>home<span style="color: #000000; font-weight: bold;">/</span>monsite<span style="color: #000000; font-weight: bold;">/</span>wordpress<span style="color: #000000; font-weight: bold;">/</span> user<span style="color: #000000; font-weight: bold;">@</span>serveurb.com:<span style="color: #000000; font-weight: bold;">/</span>home<span style="color: #000000; font-weight: bold;">/</span>monsite<span style="color: #000000; font-weight: bold;">/</span></pre></div></div>

<p><strong>3. Setup et configuration du nouveau serveur</strong><br />
Sur le serveur B:<br />
Installer les packets necessaires:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;"><span style="color: #c20cb9; font-weight: bold;">apt-get</span> <span style="color: #c20cb9; font-weight: bold;">install</span> php5-cgi php5-mysql mysql-server nginx spawn-fcgi <span style="color: #c20cb9; font-weight: bold;">sendmail</span></pre></div></div>

<p>Il faut lancer les services nginx et spawn-cgi (pour ce dernier on peut utiliser <a href="http://supervisord.org/">supervisord</a>)</p>
<p>Nginx:<br />
Editer le fichier /etc/nginx/conf.d/monsite.conf . Attention à bien indiquer le chemin absolu vers votre site pour <em>root</em></p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">server <span style="color: #7a0874; font-weight: bold;">&#123;</span>
    listen      <span style="color: #000000;">80</span>;
    server_name  monsite.com www.monsite.com;                   <span style="color: #666666; font-style: italic;"># your domain name</span>
    root         <span style="color: #000000; font-weight: bold;">/</span>home<span style="color: #000000; font-weight: bold;">/</span>monsite<span style="color: #000000; font-weight: bold;">/</span>wordpress;  <span style="color: #666666; font-style: italic;"># absolute path to your WordPress installation</span>
    index index.php index.html;
&nbsp;
    error_log <span style="color: #ff0000;">&quot;/var/log/nginx_error.log&quot;</span>;
    access_log  <span style="color: #ff0000;">&quot;/var/log/nginx_access.log&quot;</span>;
&nbsp;
    try_files <span style="color: #007800;">$uri</span> <span style="color: #007800;">$uri</span><span style="color: #000000; font-weight: bold;">/</span> <span style="color: #000000; font-weight: bold;">/</span>index.php;
&nbsp;
    location ~ \.php$ <span style="color: #7a0874; font-weight: bold;">&#123;</span>
        include        <span style="color: #000000; font-weight: bold;">/</span>etc<span style="color: #000000; font-weight: bold;">/</span>nginx<span style="color: #000000; font-weight: bold;">/</span>fastcgi_params;
        fastcgi_pass   127.0.0.1:<span style="color: #000000;">53217</span>;
        fastcgi_index index.php;
        fastcgi_buffers <span style="color: #000000;">8</span> 16k;
        fastcgi_buffer_size 32k;
        fastcgi_param  SCRIPT_FILENAME  <span style="color: #007800;">$document_root</span><span style="color: #007800;">$fastcgi_script_name</span>;
    <span style="color: #7a0874; font-weight: bold;">&#125;</span>
&nbsp;
location = <span style="color: #000000; font-weight: bold;">/</span>robots.txt <span style="color: #7a0874; font-weight: bold;">&#123;</span>
        allow all;
        log_not_found off;
        access_log off;
<span style="color: #7a0874; font-weight: bold;">&#125;</span>
&nbsp;
<span style="color: #666666; font-style: italic;"># Deny all attempts to access hidden files such as .htaccess, .htpasswd, .DS_Store (Mac).</span>
location ~ <span style="color: #000000; font-weight: bold;">/</span>\. <span style="color: #7a0874; font-weight: bold;">&#123;</span>
        deny all;
        access_log off;
        log_not_found off;
<span style="color: #7a0874; font-weight: bold;">&#125;</span>
&nbsp;
<span style="color: #666666; font-style: italic;"># Deny access to any files with a .php extension in the uploads directory</span>
location ~<span style="color: #000000; font-weight: bold;">*</span> ^<span style="color: #000000; font-weight: bold;">/</span>wp-content<span style="color: #000000; font-weight: bold;">/</span>uploads<span style="color: #000000; font-weight: bold;">/</span>.<span style="color: #000000; font-weight: bold;">*</span>.php$ <span style="color: #7a0874; font-weight: bold;">&#123;</span>
        deny all;
        access_log off;
        log_not_found off;
<span style="color: #7a0874; font-weight: bold;">&#125;</span>
&nbsp;
<span style="color: #666666; font-style: italic;"># Deny access to any files with a .php extension in the uploads directory for multisite</span>
location ~<span style="color: #000000; font-weight: bold;">*</span> <span style="color: #000000; font-weight: bold;">/</span>files<span style="color: #000000; font-weight: bold;">/</span><span style="color: #7a0874; font-weight: bold;">&#40;</span>.<span style="color: #000000; font-weight: bold;">*</span><span style="color: #7a0874; font-weight: bold;">&#41;</span>.php$ <span style="color: #7a0874; font-weight: bold;">&#123;</span>
        deny all;
        access_log off;
        log_not_found off;
<span style="color: #7a0874; font-weight: bold;">&#125;</span>
&nbsp;
<span style="color: #7a0874; font-weight: bold;">&#125;</span></pre></div></div>

<p><a href="http://serverfault.com/questions/6733/php-what-are-the-advantages-of-fastcgi-over-mod-php">Spawn-Fcgi</a>: C&#8217;est lui qui va lancer php5-cgi pour faire la liaison entre php et nginx. on va le lancer avec supervisor comme si c&#8217;était un service mais mieux.</p>
<p>Installation de Supervisor:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;"><span style="color: #c20cb9; font-weight: bold;">apt-get</span> <span style="color: #c20cb9; font-weight: bold;">install</span> python-setuptools
easy_install supervisor
echo_supervisord_conf <span style="color: #000000; font-weight: bold;">&gt;</span> <span style="color: #000000; font-weight: bold;">/</span>etc<span style="color: #000000; font-weight: bold;">/</span>supervisord.conf</pre></div></div>

<p>Editez le fichier /etc/supervisord.conf pour y rajouter spawn-fcgi, c&#8217;est mieux de lancer php5-cgi avec un user autre que root (www-data ou autre) :</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;"><span style="color: #7a0874; font-weight: bold;">&#91;</span>program:php5-cgi<span style="color: #7a0874; font-weight: bold;">&#93;</span>
<span style="color: #007800;">command</span>=<span style="color: #000000; font-weight: bold;">/</span>usr<span style="color: #000000; font-weight: bold;">/</span>local<span style="color: #000000; font-weight: bold;">/</span>bin<span style="color: #000000; font-weight: bold;">/</span>spawn-fcgi <span style="color: #660033;">-n</span> <span style="color: #660033;">-a</span> 127.0.0.1 <span style="color: #660033;">-p</span> <span style="color: #000000;">53217</span> <span style="color: #660033;">-u</span> www-data <span style="color: #660033;">-f</span> <span style="color: #000000; font-weight: bold;">/</span>usr<span style="color: #000000; font-weight: bold;">/</span>bin<span style="color: #000000; font-weight: bold;">/</span>php5-cgi
<span style="color: #007800;">redirect_stderr</span>=<span style="color: #c20cb9; font-weight: bold;">true</span> 
<span style="color: #007800;">stdout_logfile</span>=<span style="color: #000000; font-weight: bold;">/</span>var<span style="color: #000000; font-weight: bold;">/</span>log<span style="color: #000000; font-weight: bold;">/</span>php5-cgi.log
<span style="color: #007800;">stdout_logfile_maxbytes</span>=10MB</pre></div></div>

<p>Pour lancer Spawn-fcgi:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">supervisorctl restart php5-cgi</pre></div></div>

<p>Mysql: on ajoute mysql au demarrage et on le lance</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">chkconfig mysql on
service mysql start</pre></div></div>

<p>Dump de la DB: il faut créer un user et une base sur la nouvelle install, si possible le même que sur l&#8217;ancien serveur pour faciliter la transition.<br />
Sur le serveur B:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">mysql <span style="color: #660033;">-u</span> root <span style="color: #660033;">-prootpass</span>
Welcome to the MySQL monitor.  Commands end with ; or \g.
Your MySQL connection <span style="color: #c20cb9; font-weight: bold;">id</span> is <span style="color: #000000;">42</span>
Server version: 5.5.28-0ubuntu0.12.04.3 <span style="color: #7a0874; font-weight: bold;">&#40;</span>Ubuntu<span style="color: #7a0874; font-weight: bold;">&#41;</span>
&nbsp;
Copyright <span style="color: #7a0874; font-weight: bold;">&#40;</span>c<span style="color: #7a0874; font-weight: bold;">&#41;</span> <span style="color: #000000;">2000</span>, <span style="color: #000000;">2012</span>, Oracle and<span style="color: #000000; font-weight: bold;">/</span>or its affiliates. All rights reserved.
&nbsp;
Oracle is a registered trademark of Oracle Corporation and<span style="color: #000000; font-weight: bold;">/</span>or its
affiliates. Other names may be trademarks of their respective
owners.
&nbsp;
Type <span style="color: #ff0000;">'help;'</span> or <span style="color: #ff0000;">'\h'</span> <span style="color: #000000; font-weight: bold;">for</span> help. Type <span style="color: #ff0000;">'\c'</span> to <span style="color: #c20cb9; font-weight: bold;">clear</span> the current input statement.
&nbsp;
mysql<span style="color: #000000; font-weight: bold;">&gt;</span> create database base_a_toto;
Query OK, <span style="color: #000000;">1</span> row affected <span style="color: #7a0874; font-weight: bold;">&#40;</span><span style="color: #000000;">0.00</span> sec<span style="color: #7a0874; font-weight: bold;">&#41;</span>
&nbsp;
mysql<span style="color: #000000; font-weight: bold;">&gt;</span> GRANT ALL PRIVILEGES ON base_a_toto.<span style="color: #000000; font-weight: bold;">*</span> TO <span style="color: #ff0000;">&quot;user_toto&quot;</span><span style="color: #000000; font-weight: bold;">@</span><span style="color: #ff0000;">&quot;localhost&quot;</span> identified by <span style="color: #ff0000;">&quot;pass_toto&quot;</span>;
&nbsp;
Query OK, <span style="color: #000000;">0</span> rows affected <span style="color: #7a0874; font-weight: bold;">&#40;</span><span style="color: #000000;">16.16</span> sec<span style="color: #7a0874; font-weight: bold;">&#41;</span>
&nbsp;
mysql<span style="color: #000000; font-weight: bold;">&gt;</span> FLUSH PRIVILEGES;
Query OK, <span style="color: #000000;">0</span> rows affected <span style="color: #7a0874; font-weight: bold;">&#40;</span><span style="color: #000000;">0.00</span> sec<span style="color: #7a0874; font-weight: bold;">&#41;</span></pre></div></div>

<p>Et on importe la base de données de serveura.com:</p>

<div class="wp_syntax"><div class="code"><pre class="bash" style="font-family:monospace;">mysql <span style="color: #660033;">-u</span> user_toto -ppass_toto base_a_toto <span style="color: #000000; font-weight: bold;">&lt;</span> <span style="color: #000000; font-weight: bold;">/</span>tmp<span style="color: #000000; font-weight: bold;">/</span>base_a_toto.sql</pre></div></div>

<p><strong>4. Changer les dns</strong><br />
des fois on oublie :) alors changez les dns et attendez un peu, normallement ça devrait crystalliser&#8230;</p>
<p>Ca prend pas 5 minutes, même avec les paquets tous prêts. on peut avoir de mauvaises surprises en route. Moi par exemple erreur 500 , pour m&#8217;aperçevoir au bout de 2 heures que j&#8217;avais pas installé php5-mysql d&#8217;où ce tuto ;)</p>


feed_id: http://sametmax.com/?p=4070
title: Le cadeau de Noël est arrivé
uri: Le-cadeau-de-Noël-est-arrivé
url: http://sametmax.com/le-cadeau-de-noel-est-arrive/
content:
<p>Foxmask avait été choisit par notre <a href="http://sametmax.com/lun-de-vous-a-un-cadeau-de-noel-qui-lattend-au-pied-du-sapin/#comment-4955">tirage au sort à l&#8217;arrache</a>. Max et moi avions opté pour lui offrir un <a href="http://www.razerzone.com/fr-fr/gaming-mice/razer-orochi">Razer Orochi</a> car j&#8217;en possède une depuis pas mal de temps et :</p>
<ul>
<li>Comme toutes les souris razer, elle est très confortable et précise.</li>
<li>C&#8217;est une souris sans fils bluetooth, mais avec un cable optionnel si les piles tombent en panne.</li>
<li>C&#8217;est le genre de truc qu&#8217;on achète rarement soit même car ça fait mal au cul de mettre 70 € dans une souris.</li>
</ul>
<div id="attachment_4071" class="wp-caption aligncenter" style="width: 366px"><a href="http://sametmax.com/wp-content/uploads/2013/01/razer-orochi-940x573.png"><img class="size-full wp-image-4071" title="Elle a toutes les qualités d'une souris de bureau ET de nomade: taille, poids, précision, autonomie..." src="http://sametmax.com/wp-content/uploads/2013/01/razer-orochi-940x573.png" alt="Photo de la souris Razer Orochi" width="356" height="452" /></a><p class="wp-caption-text">Elle a toutes les qualités d&#39;une souris de bureau ET de nomade: taille, poids, précision, autonomie...</p></div>
<p>La livraison a par contre été plus longue que prévue.</p>
<h2>Sam et Max se décarcassent expressément</h2>
<blockquote>
<ul>
<li>Max: J&#8217;ai l&#8217;impression que Paypal a fait un mix entre l&#8217;adresse de livraison et l&#8217;adresse de facturation. Ca passera jamais&#8230;</li>
<li>Sam: Mais nannnnnnnnnnn. T&#8217;es pessimiste !</li>
</ul>
</blockquote>
<p>Une demi-heure plus tard Razer (<a href="http://www.razerzone.com/about-razer">société américaine</a> qui nous livrera depuis l&#8217;Allemagne), nous appelle en français pour nous demander de confirmer l&#8217;adresse. 5 minutes après je reçois un mail de confirmation de commande. 12 heures après une confirmation de shipping avec numéro de suivit. Les mecs sont hyper pros.</p>
<p>Après 11 jours, rien.</p>
<p>Je check sur le site de DHL, apparemment le colis est bloqué dans la grande ville la plus proche et le site crie en rouge de contacter DHL pour résoudre un <strong>problème d&#8217;adresse</strong>.</p>
<p>Je tente de les appeler. Or DHL est une entreprise internationale qui gère du courrier. En période de fête, son activité explose. Que fait DHL France, comme tout service français en cas de surcroît d&#8217;activité ? Ils <del>embauchent du personnel</del> mettent tout le monde en vacances.</p>
<p>Impossible d&#8217;avoir DHL pendant 5 jours de musique d&#8217;attente.</p>
<p>Finalement, ils me répondent que non, <em>ils n&#8217;ont pas de problème d&#8217;adresse, mais que ça doit être leur sous-traitant qui a le problème</em>. Car DHL ne livre pas partout directement, et <em>notre colis a été remis à une autre société</em>.</p>
<p><strong>Ducros-Express.</strong></p>
<p>J&#8217;ai cru à une blague, mais non, <a href="http://www.ducros-express.fr/fr/">ils ont un site Web très 1995</a> (créé avec FrontPage si vous regardez les sources).</p>
<p>J&#8217;essaye de joindre, Ducros-Express, donc. Non sans noter la nouvelle référence client qui n&#8217;est pas la même que celle de DHL. Appel, sonnerie d&#8217;attente, j&#8217;apprends que &#8220;Ducros-Express, it&#8217;s more that 3000 professionals to support you around the world&#8221; (ouai, en anglais, si, si) mais qu&#8217;ils sont tous en vacances. Car c&#8217;est les fêtes, que leur activité explose, et que comme toute entreprise française&#8230;</p>
<p>Bref.</p>
<p>Je les appelle hors fête, me heurtant plusieurs fois au fait qu&#8217;ils sont pas dispo le midi. Car quand on a &#8220;3000 professionals around the world&#8221; et qu&#8217;on fait de la livraison Express, on a des horaires 9h-12h, 14h-17h. Logique.</p>
<p>Une fois que je les ai au téléphone, ils me répondent que non, <em>ils n&#8217;ont pas de problème d&#8217;adresse, mais que ça doit être leur sous-traitant qui a le problème</em>. Car Ducros-Express ne livre pas partout directement, et <em>notre colis a été remis à une autre société</em>.</p>
<p><strong>Quercy-Messagerie.</strong></p>
<p>Je crois a une blague, mais non, <del>ils ont un site Web</del> <a href="http://www.societe.com/societe/quercy-398785352.html">ils sont enregistrés à la chambre de commerce</a>.</p>
<p>Je les appelle, réponse immédiate de Janine, qui n&#8217;est pas around the World mais qui connaît bien son boulot. <strong>Non y a pas de problème d&#8217;adresse</strong>. On peut vous livrer demain vers 14h ?</p>
<p>10h du mat, un homme avec un mélange d&#8217;accent local et lointain me téléphone. Oui il sait très bien où c&#8217;est, c&#8217;est en dessous de chez M. X (WTF ? Comment il sait ça ? C&#8217;est un lieu dit avec 100 habitants à 10 bornes de toute ville). Faudra descendre en bas de la pente car le camion passera pas. J&#8217;arrive dans 15 minutes.</p>
<p>Récupération du colis, reconditionnement bonbon + capote + pillule de viagra. Reexpédition vers l&#8217;adresse de Foxmask (je saiiiiiiiiiiiiiiiiiiiis où tu habiiiiiiiiiiiiiiiiiiiiiiiiiiiiiite).</p>
<p>Ta da :</p>
<div id="attachment_4072" class="wp-caption aligncenter" style="width: 310px"><a href="http://sametmax.com/wp-content/uploads/2013/01/2013-01-08-19.05.42-300x225.jpg"><img class="size-full wp-image-4072" title="La fraise tagada fait un très bon papier à bulle." src="http://sametmax.com/wp-content/uploads/2013/01/2013-01-08-19.05.42-300x225.jpg" alt="Photo de bonbons" width="300" height="225" /></a><p class="wp-caption-text">La fraise tagada fait un très bon papier à bulle.</p></div>
<div id="attachment_4073" class="wp-caption aligncenter" style="width: 235px"><a href="http://sametmax.com/wp-content/uploads/2013/01/2013-01-08-19.06.30-225x300.jpg"><img class="size-full wp-image-4073" title="Il manque la pillule de viagra, qui a du tombé dans les bonbons. Que ses gosses ont bouffé..." src="http://sametmax.com/wp-content/uploads/2013/01/2013-01-08-19.06.30-225x300.jpg" alt="Photo de boite de Razer Orochi" width="225" height="300" /></a><p class="wp-caption-text">Il manque la pillule de viagra, qui a du tombé dans les bonbons. Que ses gosses ont bouffé...</p></div>
<p><a href="http://www.foxmask.info/post/2013/01/08/sam-max-le-papa-noel-descendu-du-ciel/2013-01-08-19-06-30/">Le reste sur le blog de foxmask.</a></p>


feed_id: http://sametmax.com/?p=3025
title: Citations sur les prostitués
uri: Citations-sur-les-prostitués
url: http://sametmax.com/citations-sur-les-prostitues/
content:
<p>C&#8217;est pas parcequ&#8217;on a rien à dire qu&#8217;il faut fermer sa gueule&#8230; Alors comme aujourd&#8217;hui j&#8217;ai pas envie de me casser le dard je vous sors une liste de citations à placer dans vos soirées mondaines&#8230; Façon puzzle&#8230;</p>
<p>Ma préférence allant à Monsieur Simenon:</p>
<blockquote><p>Les filles que l&#8217;on paie ne sont pas celles qui nous coûtent le plus cher&#8230;</p></blockquote>
<p><strong>Alphonse Allais</strong></p>
<blockquote><p>Un amant, c&#8217;est de l&#8217;amour. Deux amants, c&#8217;est du tempérament. Trois amants, c&#8217;est du commerce.</p></blockquote>
<p><strong>Arletty</strong></p>
<blockquote><p>Fermer les maisons closes, c&#8217;est plus qu&#8217;un crime, c&#8217;est un pléonasme.</p></blockquote>
<p><strong>Auguste Renoir Racontant ses souvenirs de bordels en compagnie de ses vieux amis Alphonse Daudet et Claude Monet.<br />
</strong></p>
<blockquote><p>Alphonse les séduisait, Claude les émoustillait et moi j&#8217;en profitais !</p></blockquote>
<p><strong>Bernard Dimey</strong></p>
<blockquote><p>Quand on n&#8217;a que son cul, mais qu&#8217;on a la jeunesse, on a l&#8217;île aux Trésors à portée de la main.</p></blockquote>
<p><strong>Caroline Otero, dite &#8220;La Belle Otero&#8221;</strong></p>
<blockquote><p>La fortune ne vient pas en dormant seule</p></blockquote>
<p><strong>Elisabeth Badinter</strong></p>
<blockquote><p>La prostitution relève du droit chèrement acquis à disposer librement de son corps.</p></blockquote>
<p><strong>Étienne Rey</strong></p>
<blockquote><p>Il y a un amour que l&#8217;on appelle vénal pour laisser croire que l&#8217;autre ne se vend pas.</p></blockquote>
<p><strong>François Cavanna</strong></p>
<blockquote><p>Nul n&#8217;a pas le droit de critiquer les putes qui font correctement leur métier !</p></blockquote>
<p><strong>Frédéric Beigbeder</strong></p>
<blockquote><p>Tout s&#8217;achète : l&#8217;amour, l&#8217;art, la planète Terre, vous, moi.</p></blockquote>
<p><strong>Frédéric Dard</strong></p>
<blockquote><p>La prostitution marcherait moins bien si les hommes n&#8217;avaient pas besoin de se confier à tout prix.</p></blockquote>
<blockquote><p>Quand vous dégustez des tagliatelles au restaurant alors que vous auriez pu vous en faire à la maison, il ne viendrait à l&#8217;idée de quiconque de dire que vous faites quelque chose d&#8217;immoral. Par contre quand vous payez pour du sexe, tous les moralistes vous sautent sur le paletot !</p></blockquote>
<p><strong>Georges Clemenceau</strong></p>
<blockquote><p>Payer pour le sexe ? Pourquoi pas ? Vous payez bien pour Dieu !</p></blockquote>
<p><strong>Georges Simenon</strong></p>
<blockquote><p>Le jour de la Saint Valentin je n&#8217;irais pas voir une putain, parce que je n&#8217;aime pas ce mot, mais j&#8217;irais quand même&#8230; et je lui apporterai des fleurs.</p></blockquote>
<blockquote><p>Les filles que l&#8217;on paie ne sont pas celles qui nous coûtent le plus cher&#8230;</p></blockquote>
<p><strong>Henri Jeanson</strong></p>
<blockquote><p>Les prostituées sont des femmes du monde à l&#8217;état brut.</p></blockquote>
<p><strong>Honoré de Balzac</strong></p>
<blockquote><p>Toute femme a sa fortune entre ses jambes.</p></blockquote>
<p><strong>Jean Yanne</strong></p>
<blockquote><p>Ce qui distingue une putain d&#8217;une honnête femme, c&#8217;est qu&#8217;une putain fait le bonheur de beaucoup d&#8217;hommes tandis qu&#8217;une honnête femme fait le malheur d&#8217;un seul.</p></blockquote>
<blockquote><p>Il est faux de dire que pour obtenir une femme, il faut soit du temps soit de l’argent. De l’argent il en faudra toujours, par contre vous pouvez gagner du temps.</p></blockquote>
<p><strong>Mae West</strong></p>
<blockquote><p>Un homme amoureux est comme un coupon de réduction, il faut le faire passer à la caisse sans plus attendre.</p></blockquote>
<p><strong>Michel Simon</strong></p>
<blockquote><p>Il y a un point commun entre les chats et les prostituées, c&#8217;est que pour obtenir leur affection, il faut le mériter.</p></blockquote>
<p><strong>Molière</strong></p>
<blockquote><p>L&#8217;écriture ressemble à la prostitution. D&#8217;abord on écrit pour l&#8217;amour de la chose, puis pour quelques amis, et à la fin, pour de l&#8217;argent.</p></blockquote>
<p><strong>Paul Gavarni </strong></p>
<blockquote><p>Pourquoi mépriser les prostituées ? Ce sont des femmes qui gagnent à être connues.</p></blockquote>
<p><strong>Pierre Dac</strong></p>
<blockquote><p>Les femmes de mœurs légères ont parfois la tâche lourde avec les hommes de poids.</p></blockquote>
<p><strong>Philippe Bouvard</strong></p>
<blockquote><p>La prostitution est une des rares professions qui soient demeurées très artisanales en dépit du progrès technique.</p></blockquote>
<p><strong>Sacha Guitry</strong></p>
<blockquote><p>Commence jeune à payer les femmes, tu t&#8217;apercevras moins vite que tu vieillis&#8230;</p></blockquote>
<p><strong>Victor Hugo</strong></p>
<blockquote><p>La femme est obligée de choisir entre acheter un homme, ce qui s&#8217;appelle le mariage, ou se vendre aux hommes, ce qui s&#8217;appelle la prostitution.</p></blockquote>
<p><strong>Virginie Despentes</strong></p>
<blockquote><p>Quand on affirme que la prostitution est une &#8220;violence faite aux femmes&#8221;, on veut nous faire oublier que c&#8217;est la mariage qui est &#8220;une violence faite aux femmes&#8221;.</p></blockquote>
<p>Et je concluerais:<br />
<strong>A poil les putes !</strong></p>


