<?xml version="1.0" encoding="UTF-8"?>
<rss version="2.0"
	xmlns:content="http://purl.org/rss/1.0/modules/content/"
	xmlns:wfw="http://wellformedweb.org/CommentAPI/"
	xmlns:dc="http://purl.org/dc/elements/1.1/"
	xmlns:atom="http://www.w3.org/2005/Atom"
	xmlns:sy="http://purl.org/rss/1.0/modules/syndication/"
	xmlns:slash="http://purl.org/rss/1.0/modules/slash/"
	>

<channel>
	<title>Coder-Studio &#187; haskell</title>
	<atom:link href="http://www.coder-studio.com/blog/tag/haskell/feed/" rel="self" type="application/rss+xml" />
	<link>http://www.coder-studio.com/blog</link>
	<description></description>
	<lastBuildDate>Wed, 31 Mar 2010 00:00:53 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.9.2</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>(Petit) Clône de client telnet en Haskell</title>
		<link>http://www.coder-studio.com/blog/petit-clone-de-client-telnet-en-haskell/</link>
		<comments>http://www.coder-studio.com/blog/petit-clone-de-client-telnet-en-haskell/#comments</comments>
		<pubDate>Fri, 28 Aug 2009 11:19:08 +0000</pubDate>
		<dc:creator>Alp Mestan</dc:creator>
				<category><![CDATA[Langages fonctionnels]]></category>
		<category><![CDATA[fonctionnel]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[telnet]]></category>

		<guid isPermaLink="false">http://www.coder-studio.com/blog/?p=421</guid>
		<description><![CDATA[Bonjour,
L&#8217;autre nuit, muni de café, j&#8217;ai souhaité m&#8217;amuser avec Haskell. J&#8217;ai alors consulté le chapitre sur le réseau en Haskell de Real World Haskell et&#8230; j&#8217;ai écrit un (très petit) clône de client telnet&#8230; qui fait 41 lignes. Le seul soucis étant que dans toute application de ce genre, on doit partager habilement la lecture [...]]]></description>
			<content:encoded><![CDATA[<p>Bonjour,</p>
<p>L&#8217;autre nuit, muni de café, j&#8217;ai souhaité m&#8217;amuser avec Haskell. J&#8217;ai alors consulté le chapitre sur le réseau en Haskell de <a href="http://book.realworldhaskell.org/read/">Real World Haskell</a> et&#8230; j&#8217;ai écrit un (très petit) clône de client telnet&#8230; qui fait 41 lignes. Le seul soucis étant que dans toute application de ce genre, on doit partager habilement la lecture des entrées de l&#8217;utilisateur, et l&#8217;affichage de ce que l&#8217;on nous envoie. Ceci mis à part, tout cela fonctionne très bien !</p>
<p><center><img src="http://haskell.org/logos/logos/logo7000.png" alt="Haskell" title="Haskell" /></center></p>
<p><span id="more-421"></span></p>
<p>Regardons à quoi cela ressemble. Petit détail : à chaque tour, je lance la réception de données réseau dans un autre thread, pour ne pas bloquer l&#8217;écriture de l&#8217;utilisateur.</p>
<p>On importe d&#8217;abord les modules nécessaires.</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p421code8'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p4218"><td class="code" id="p421code8"><pre class="haskell" style="font-family:monospace;"><span style="color: #06c; font-weight: bold;">import</span> Control<span style="color: #339933; font-weight: bold;">.</span>Concurrent 
<span style="color: #06c; font-weight: bold;">import</span> Control<span style="color: #339933; font-weight: bold;">.</span><a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:Monad"><span style="color: #cccc00; font-weight: bold;">Monad</span></a> 
<span style="color: #06c; font-weight: bold;">import</span> Network<span style="color: #339933; font-weight: bold;">.</span>Socket 
<span style="color: #06c; font-weight: bold;">import</span> Network<span style="color: #339933; font-weight: bold;">.</span>BSD 
<span style="color: #06c; font-weight: bold;">import</span> System<span style="color: #339933; font-weight: bold;">.</span>Environment 
<span style="color: #06c; font-weight: bold;">import</span> System<span style="color: #339933; font-weight: bold;">.</span><a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a></pre></td></tr></table></div>

<p>Ensuite, j&#8217;ai écrit quelques fonctions pour rendre la connection, l&#8217;envoi etc plus faciles.</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p421code9'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p4219"><td class="code" id="p421code9"><pre class="haskell" style="font-family:monospace;"><span style="color: #5d478b; font-style: italic;">-- Ouverture d'une connexion TCP cliente </span>
<span style="color: #5d478b; font-style: italic;">-- Prend en argument l'host et le port/service (qui est une String également) </span>
<span style="color: #5d478b; font-style: italic;">-- Retourne le &quot;Handle&quot; vers le socket en question. </span>
openConnection <span style="color: #339933; font-weight: bold;">::</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> ServiceName <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> Handle 
openConnection hostname port <span style="color: #339933; font-weight: bold;">=</span> 
  <span style="color: #06c; font-weight: bold;">do</span> 
  addrInfos <span style="color: #339933; font-weight: bold;">&lt;-</span> getAddrInfo Nothing <span style="color: green;">&#40;</span>Just hostname<span style="color: green;">&#41;</span> <span style="color: green;">&#40;</span>Just port<span style="color: green;">&#41;</span> 
  <span style="color: #06c; font-weight: bold;">let</span> serveraddr <span style="color: #339933; font-weight: bold;">=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:head"><span style="font-weight: bold;">head</span></a> addrInfos 
  sock <span style="color: #339933; font-weight: bold;">&lt;-</span> socket <span style="color: green;">&#40;</span>addrFamily serveraddr<span style="color: green;">&#41;</span> Stream defaultProtocol 
  setSocketOption sock KeepAlive <span style="color: red;">1</span> 
  connect sock <span style="color: green;">&#40;</span>addrAddress serveraddr<span style="color: green;">&#41;</span> 
  h <span style="color: #339933; font-weight: bold;">&lt;-</span> socketToHandle sock ReadWriteMode 
  hSetBuffering h <span style="color: green;">&#40;</span>BlockBuffering Nothing<span style="color: green;">&#41;</span> 
  <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:return"><span style="font-weight: bold;">return</span></a> h 
&nbsp;
<span style="color: #5d478b; font-style: italic;">-- Ferme la connexion dont le Handle est donné </span>
closeConnection <span style="color: #339933; font-weight: bold;">::</span> Handle <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> <span style="color: green;">&#40;</span><span style="color: green;">&#41;</span> 
closeConnection h <span style="color: #339933; font-weight: bold;">=</span> hClose h 
&nbsp;
<span style="color: #5d478b; font-style: italic;">-- Envoie la chaîne donnée sur le Handle donné, et ensuite fait un flush sur ce handle, ce qui force l'envoi immédiat et nettoie les états </span>
sendMsg <span style="color: #339933; font-weight: bold;">::</span> Handle <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> <span style="color: green;">&#40;</span><span style="color: green;">&#41;</span> 
sendMsg h msg <span style="color: #339933; font-weight: bold;">=</span> hPutStrLn h msg <span style="color: #339933; font-weight: bold;">&gt;&gt;</span> hFlush h 
&nbsp;
<span style="color: #5d478b; font-style: italic;">-- Lis sur le Handle donné une chaîne et la renvoie (dans la monade IO) </span>
recvMsg <span style="color: #339933; font-weight: bold;">::</span> Handle <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a> 
recvMsg h <span style="color: #339933; font-weight: bold;">=</span> <span style="color: #06c; font-weight: bold;">do</span> 
  msg <span style="color: #339933; font-weight: bold;">&lt;-</span> hGetContents h  
  <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:return"><span style="font-weight: bold;">return</span></a> msg</pre></td></tr></table></div>

<p>Voyons maintenant la fonction main.</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p421code10'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p42110"><td class="code" id="p421code10"><pre class="haskell" style="font-family:monospace;">main <span style="color: #339933; font-weight: bold;">=</span> <span style="color: #06c; font-weight: bold;">do</span> 
  args <span style="color: #339933; font-weight: bold;">&lt;-</span> getArgs 
  <span style="color: #06c; font-weight: bold;">let</span> <span style="color: green;">&#40;</span>host<span style="color: #339933; font-weight: bold;">,</span> port<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">=</span> <span style="color: green;">&#40;</span>args <span style="color: #339933; font-weight: bold;">!!</span> <span style="color: red;">0</span><span style="color: #339933; font-weight: bold;">,</span> args <span style="color: #339933; font-weight: bold;">!!</span> <span style="color: red;">1</span><span style="color: green;">&#41;</span></pre></td></tr></table></div>

<p>On récupère les arguments donnés au programme (s&#8217;il n&#8217;y en a pas assez, cela fera planter le logiciel &#8212; je ne me suis pas vraiment préoccupé de tous les cas d&#8217;erreur, mais ce n&#8217;était pas ma priorité ici) via la fonction getArgs, et l&#8217;on en récupère l&#8217;host et le port donnés.</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p421code11'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p42111"><td class="code" id="p421code11"><pre class="haskell" style="font-family:monospace;">  <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="color: #339933; font-weight: bold;">$</span> <span style="background-color: #3cb371;">&quot;Opening client on &quot;</span> <span style="color: #339933; font-weight: bold;">++</span> host <span style="color: #339933; font-weight: bold;">++</span> <span style="background-color: #3cb371;">&quot;:&quot;</span> <span style="color: #339933; font-weight: bold;">++</span> port <span style="color: #339933; font-weight: bold;">++</span> <span style="background-color: #3cb371;">&quot;<span style="background-color: #3cb371; font-weight: bold;">\n</span>&quot;</span> 
  hclient <span style="color: #339933; font-weight: bold;">&lt;-</span> openConnection host port 
  <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="background-color: #3cb371;">&quot;Client connected&quot;</span></pre></td></tr></table></div>

<p>Ca y est, on se connecte, en affichant des messages pour tenir l&#8217;utilisateur informé. Si la connection échoue, le programme s&#8217;arrêtera avec une erreur &#8212; cf remarque ci-dessus.</p>
<p>Et maintenant, la boucle qui permet de lire depuis le réseau et lire depuis l&#8217;utilisateur, etc.</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p421code12'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p42112"><td class="code" id="p421code12"><pre class="haskell" style="font-family:monospace;">  forever <span style="color: #339933; font-weight: bold;">$</span> <span style="color: #06c; font-weight: bold;">do</span> 
    <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:getLine"><span style="font-weight: bold;">getLine</span></a> <span style="color: #339933; font-weight: bold;">&gt;&gt;=</span> sendMsg hclient 
    forkIO <span style="color: #339933; font-weight: bold;">$</span> recvMsg hclient <span style="color: #339933; font-weight: bold;">&gt;&gt;=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a></pre></td></tr></table></div>

<p>Ici, on a une sorte de boucle &laquo;&nbsp;à la while(true)&nbsp;&raquo;, dans laquelle on va tour à tour récupérer une entrée de l&#8217;utilisateur et l&#8217;envoyer au serveur, puis, dans un thread séparé, récupérer ce qu&#8217;a envoyé le serveur et l&#8217;afficher.<br />
Enfin, on ferme la connection (ce code est inutile tant que l&#8217;on a pas de possibilité de sortir du forever&#8230; qui devra tôt ou tard se transformer en &laquo;&nbsp;until&nbsp;&raquo; ou autre).</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p421code13'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p42113"><td class="code" id="p421code13"><pre class="haskell" style="font-family:monospace;">  closeConnection hclient</pre></td></tr></table></div>

<p>Voilà le code complet :</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p421code14'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p42114"><td class="code" id="p421code14"><pre class="haskell" style="font-family:monospace;"><span style="color: #06c; font-weight: bold;">import</span> Control<span style="color: #339933; font-weight: bold;">.</span>Concurrent 
<span style="color: #06c; font-weight: bold;">import</span> Control<span style="color: #339933; font-weight: bold;">.</span><a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:Monad"><span style="color: #cccc00; font-weight: bold;">Monad</span></a> 
<span style="color: #06c; font-weight: bold;">import</span> Network<span style="color: #339933; font-weight: bold;">.</span>Socket 
<span style="color: #06c; font-weight: bold;">import</span> Network<span style="color: #339933; font-weight: bold;">.</span>BSD 
<span style="color: #06c; font-weight: bold;">import</span> System<span style="color: #339933; font-weight: bold;">.</span>Environment 
<span style="color: #06c; font-weight: bold;">import</span> System<span style="color: #339933; font-weight: bold;">.</span><a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> 
&nbsp;
openConnection <span style="color: #339933; font-weight: bold;">::</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> ServiceName <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> Handle 
openConnection hostname port <span style="color: #339933; font-weight: bold;">=</span> <span style="color: #06c; font-weight: bold;">do</span> 
  addrInfos <span style="color: #339933; font-weight: bold;">&lt;-</span> getAddrInfo Nothing <span style="color: green;">&#40;</span>Just hostname<span style="color: green;">&#41;</span> <span style="color: green;">&#40;</span>Just port<span style="color: green;">&#41;</span> 
  <span style="color: #06c; font-weight: bold;">let</span> serveraddr <span style="color: #339933; font-weight: bold;">=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:head"><span style="font-weight: bold;">head</span></a> addrInfos 
  sock <span style="color: #339933; font-weight: bold;">&lt;-</span> socket <span style="color: green;">&#40;</span>addrFamily serveraddr<span style="color: green;">&#41;</span> Stream defaultProtocol 
  setSocketOption sock KeepAlive <span style="color: red;">1</span> 
  connect sock <span style="color: green;">&#40;</span>addrAddress serveraddr<span style="color: green;">&#41;</span> 
  h <span style="color: #339933; font-weight: bold;">&lt;-</span> socketToHandle sock ReadWriteMode 
  hSetBuffering h <span style="color: green;">&#40;</span>BlockBuffering Nothing<span style="color: green;">&#41;</span> 
  <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:return"><span style="font-weight: bold;">return</span></a> h 
&nbsp;
closeConnection <span style="color: #339933; font-weight: bold;">::</span> Handle <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> <span style="color: green;">&#40;</span><span style="color: green;">&#41;</span> 
closeConnection h <span style="color: #339933; font-weight: bold;">=</span> hClose h 
&nbsp;
sendMsg <span style="color: #339933; font-weight: bold;">::</span> Handle <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> <span style="color: green;">&#40;</span><span style="color: green;">&#41;</span> 
sendMsg h msg <span style="color: #339933; font-weight: bold;">=</span> hPutStrLn h msg <span style="color: #339933; font-weight: bold;">&gt;&gt;</span> hFlush h 
&nbsp;
recvMsg <span style="color: #339933; font-weight: bold;">::</span> Handle <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a> 
recvMsg h <span style="color: #339933; font-weight: bold;">=</span> <span style="color: #06c; font-weight: bold;">do</span> 
  msg <span style="color: #339933; font-weight: bold;">&lt;-</span> hGetContents h  
  <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:return"><span style="font-weight: bold;">return</span></a> msg 
&nbsp;
main <span style="color: #339933; font-weight: bold;">=</span> <span style="color: #06c; font-weight: bold;">do</span> 
  args <span style="color: #339933; font-weight: bold;">&lt;-</span> getArgs 
  <span style="color: #06c; font-weight: bold;">let</span> <span style="color: green;">&#40;</span>host<span style="color: #339933; font-weight: bold;">,</span> port<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">=</span> <span style="color: green;">&#40;</span>args <span style="color: #339933; font-weight: bold;">!!</span> <span style="color: red;">0</span><span style="color: #339933; font-weight: bold;">,</span> args <span style="color: #339933; font-weight: bold;">!!</span> <span style="color: red;">1</span><span style="color: green;">&#41;</span> 
  <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="color: #339933; font-weight: bold;">$</span> <span style="background-color: #3cb371;">&quot;Opening client on &quot;</span> <span style="color: #339933; font-weight: bold;">++</span> host <span style="color: #339933; font-weight: bold;">++</span> <span style="background-color: #3cb371;">&quot;:&quot;</span> <span style="color: #339933; font-weight: bold;">++</span> port <span style="color: #339933; font-weight: bold;">++</span> <span style="background-color: #3cb371;">&quot;<span style="background-color: #3cb371; font-weight: bold;">\n</span>&quot;</span> 
  hclient <span style="color: #339933; font-weight: bold;">&lt;-</span> openConnection host port 
  <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="background-color: #3cb371;">&quot;Client connected&quot;</span> 
  forever <span style="color: #339933; font-weight: bold;">$</span> <span style="color: #06c; font-weight: bold;">do</span> 
    <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:getLine"><span style="font-weight: bold;">getLine</span></a> <span style="color: #339933; font-weight: bold;">&gt;&gt;=</span> sendMsg hclient 
    forkIO <span style="color: #339933; font-weight: bold;">$</span> recvMsg hclient <span style="color: #339933; font-weight: bold;">&gt;&gt;=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> 
  closeConnection hclient</pre></td></tr></table></div>

<p>Compilation :</p>
<blockquote><p>ghc &#8211;make -o net net.hs</p></blockquote>
<p>Puis 2 exemples d&#8217;exécution&#8230;<br />
<code>
<pre>
$ ./net google.fr 80
Opening client on google.fr:80
Client connected
GET / HTTP/1.0
HTTP/1.0 302 Found
Location: http://www.google.fr/
Cache-Control: private
Content-Type: text/html; charset=UTF-8
Set-Cookie: PREF=ID=30b094ad566b5532:TM=1251456529:LM=1251456529:S=94IXp5-SGiaYADWc; expires=Sun, 28-Aug-2011 10:48:49 GMT; path=/; domain=.google.com
Date: Fri, 28 Aug 2009 10:48:49 GMT
Server: gws
Content-Length: 218 

<HTML><HEAD><meta http-equiv="content-type" content="text/html;charset=utf-8">
<TITLE>302 Moved</TITLE></HEAD><BODY>
<H1>302 Moved</H1>
The document has moved
<A HREF="http://www.google.fr/">here</A>.
</BODY></HTML> 

^C
</pre>
<p></code><br />
(c&#8217;est moi qui ai tapé &laquo;&nbsp;GET / HTTP/1.0&#8243;)<br />
( qui vous dira que la page a été déplacée <img src='http://www.coder-studio.com/blog/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' />  )</p>
<p>Et enfin, la surprise&#8230;</p>
<blockquote><p>$ ./net towel.blinkenlights.nl 23</p></blockquote>
<p>Qui, une version simplifiée d&#8217;un film très connu, vous permettra de voir, Jedi.</p>
<p>Enjoy !</p>
]]></content:encoded>
			<wfw:commentRss>http://www.coder-studio.com/blog/petit-clone-de-client-telnet-en-haskell/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>Haskell Platform, ou comment se mettre à Haskell sans soucis !</title>
		<link>http://www.coder-studio.com/blog/haskell-platform-ou-comment-se-mettre-a-haskell-sans-soucis/</link>
		<comments>http://www.coder-studio.com/blog/haskell-platform-ou-comment-se-mettre-a-haskell-sans-soucis/#comments</comments>
		<pubDate>Wed, 12 Aug 2009 08:19:14 +0000</pubDate>
		<dc:creator>Alp Mestan</dc:creator>
				<category><![CDATA[Langages fonctionnels]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[platform]]></category>

		<guid isPermaLink="false">http://www.coder-studio.com/blog/?p=401</guid>
		<description><![CDATA[Bonjour à tous,
Cela fait quelques temps maintenant que la communauté Haskell a sorti Haskell Platform. Il s&#8217;agit d&#8217;un &#171;&#160;paquet&#160;&#187; qui regroupe :
- le compilateur haskell GHC, un debugger, un profiler, etc
- les bibliothèques les plus populaires et les plus utilisées, fournies d&#8217;office
- tout un tas d&#8217;outils auxiliaires, comme haddock, qui permet de générer de la [...]]]></description>
			<content:encoded><![CDATA[<p>Bonjour à tous,</p>
<p>Cela fait quelques temps maintenant que la communauté <a href="http://www.haskell.org/">Haskell</a> a sorti <strong><a href="http://hackage.haskell.org/platform/">Haskell Platform</a></strong>. Il s&#8217;agit d&#8217;un &laquo;&nbsp;paquet&nbsp;&raquo; qui regroupe :<br />
- le compilateur haskell GHC, un debugger, un profiler, etc<br />
- les bibliothèques les plus populaires et les plus utilisées, fournies d&#8217;office<br />
- tout un tas d&#8217;outils auxiliaires, comme <em>haddock</em>, qui permet de générer de la documentation depuis les commentaires du code source.</p>
<p>Il existe des paquets pour déjà quelques distributions Linux, sachant que ce sera bientôt prêt pour Debian et Ubuntu également. Les installeurs Windows et Mac sont très simples également.</p>
<p>Bref, plus aucune raison de ne pas essayer Haskell <img src='http://www.coder-studio.com/blog/wp-includes/images/smilies/icon_smile.gif' alt=':)' class='wp-smiley' /> </p>
]]></content:encoded>
			<wfw:commentRss>http://www.coder-studio.com/blog/haskell-platform-ou-comment-se-mettre-a-haskell-sans-soucis/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>GTK+ en Haskell</title>
		<link>http://www.coder-studio.com/blog/gtk-en-haskell/</link>
		<comments>http://www.coder-studio.com/blog/gtk-en-haskell/#comments</comments>
		<pubDate>Tue, 16 Jun 2009 02:37:15 +0000</pubDate>
		<dc:creator>Alp Mestan</dc:creator>
				<category><![CDATA[Langages fonctionnels]]></category>
		<category><![CDATA[glade]]></category>
		<category><![CDATA[gtk]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[xml]]></category>

		<guid isPermaLink="false">http://www.coder-studio.com/blog/?p=342</guid>
		<description><![CDATA[Bonjour,
M&#8217;étant mis à Haskell depuis quelques temps (principalement grâce au désormais fameux Real World Haskell), je me suis dis qu&#8217;il était temps que je regarde un peu du côté des bibliothèques pour interfaces utilisateurs. Hé bien, je n&#8217;ai pas été déçu. Il y a notamment Gtk2Hs qui fournit un bon binding de GTK+, compatible avec [...]]]></description>
			<content:encoded><![CDATA[<p>Bonjour,</p>
<p>M&#8217;étant mis à Haskell depuis quelques temps (principalement grâce au désormais fameux <a href="http://general.developpez.com/livres/general/?page=prog-fonctionnelle#L9780596514983">Real World Haskell</a>), je me suis dis qu&#8217;il était temps que je regarde un peu du côté des bibliothèques pour interfaces utilisateurs. Hé bien, je n&#8217;ai pas été déçu. Il y a notamment <strong>Gtk2Hs</strong> qui fournit un bon binding de GTK+, compatible avec Glade (le designer) et qui permet donc de charger des interfaces depuis du XML.</p>
<p><center><img src="http://blog.developpez.com/media/gtk2hs.png" width="409" height="297" alt="Gtk2Hs en action" /></center></p>
<p><span id="more-342"></span></p>
<p>Allez-y, devinez combien de lignes il a fallu ?<br />
Initialiser le GUI, créer les widgets, &#8230; Hmm beaucoup ?</p>
<p>Hé bien non ! Le designer, Glade, exporte le &laquo;&nbsp;projet&nbsp;&raquo; suivant dans un XML.</p>
<p><center><img src="http://blog.developpez.com/media/glade.png" width="700" height="370" alt="Designer de fenêtres de GTK+" /></center></p>
<p>XML généré :</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p342code17'); return false;">View Code</a> XML</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p34217"><td class="code" id="p342code17"><pre class="xml" style="font-family:monospace;"><span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;?xml</span> <span style="color: #000066;">version</span>=<span style="color: #ff0000;">&quot;1.0&quot;</span><span style="color: #000000; font-weight: bold;">?&gt;</span></span> 
<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;glade-interface<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #808080; font-style: italic;">&lt;!-- interface-requires gtk+ 2.16 --&gt;</span> 
  <span style="color: #808080; font-style: italic;">&lt;!-- interface-naming-policy project-wide --&gt;</span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;widget</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;GtkWindow&quot;</span> <span style="color: #000066;">id</span>=<span style="color: #ff0000;">&quot;window1&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;property</span> <span style="color: #000066;">name</span>=<span style="color: #ff0000;">&quot;title&quot;</span> <span style="color: #000066;">translatable</span>=<span style="color: #ff0000;">&quot;yes&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>Hello, Developpez !<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/property<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;property</span> <span style="color: #000066;">name</span>=<span style="color: #ff0000;">&quot;default_width&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>400<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/property<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;property</span> <span style="color: #000066;">name</span>=<span style="color: #ff0000;">&quot;default_height&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>400<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/property<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;child<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;widget</span> <span style="color: #000066;">class</span>=<span style="color: #ff0000;">&quot;GtkButton&quot;</span> <span style="color: #000066;">id</span>=<span style="color: #ff0000;">&quot;yo&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;property</span> <span style="color: #000066;">name</span>=<span style="color: #ff0000;">&quot;label&quot;</span> <span style="color: #000066;">translatable</span>=<span style="color: #ff0000;">&quot;yes&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>Bonjour Developpez, comment vas-tu ? 
&nbsp;
Je suis un programme Haskell qui utilise 
Gtk2Hs, binding Haskell de GTK+. 
&nbsp;
Clique pour fermer.<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/property<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;property</span> <span style="color: #000066;">name</span>=<span style="color: #ff0000;">&quot;visible&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>True<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/property<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;property</span> <span style="color: #000066;">name</span>=<span style="color: #ff0000;">&quot;can_focus&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>True<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/property<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;property</span> <span style="color: #000066;">name</span>=<span style="color: #ff0000;">&quot;receives_default&quot;</span><span style="color: #000000; font-weight: bold;">&gt;</span></span>True<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/property<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/widget<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/child<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
  <span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/widget<span style="color: #000000; font-weight: bold;">&gt;</span></span></span> 
<span style="color: #009900;"><span style="color: #000000; font-weight: bold;">&lt;/glade-interface<span style="color: #000000; font-weight: bold;">&gt;</span></span></span></pre></td></tr></table></div>

<p>Et voilà, l&#8217;essentiel est fait.</p>
<p>Voici donc le main.hs, qui est le programme Haskell dont vous avez vu un screenshot plus haut :</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p342code18'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p34218"><td class="code" id="p342code18"><pre class="haskell" style="font-family:monospace;"><span style="color: #06c; font-weight: bold;">module</span> Main <span style="color: #06c; font-weight: bold;">where</span> 
&nbsp;
<span style="color: #06c; font-weight: bold;">import</span> Graphics<span style="color: #339933; font-weight: bold;">.</span>UI<span style="color: #339933; font-weight: bold;">.</span>Gtk <span style="color: #5d478b; font-style: italic;">-- on importe le module GTK </span>
<span style="color: #06c; font-weight: bold;">import</span> Graphics<span style="color: #339933; font-weight: bold;">.</span>UI<span style="color: #339933; font-weight: bold;">.</span>Gtk<span style="color: #339933; font-weight: bold;">.</span>Glade <span style="color: #5d478b; font-style: italic;">-- et le module Glade, pour créer une IHM depuis le XML au format Glade </span>
&nbsp;
main <span style="color: #339933; font-weight: bold;">=</span> <span style="color: #06c; font-weight: bold;">do</span> 
  initGUI 
  Just xml <span style="color: #339933; font-weight: bold;">&lt;-</span> xmlNew <span style="background-color: #3cb371;">&quot;test.glade&quot;</span>  
  window <span style="color: #339933; font-weight: bold;">&lt;-</span> xmlGetWidget xml castToWindow <span style="background-color: #3cb371;">&quot;window1&quot;</span> 
  button <span style="color: #339933; font-weight: bold;">&lt;-</span> xmlGetWidget xml castToButton <span style="background-color: #3cb371;">&quot;yo&quot;</span> 
  onClicked button <span style="color: #339933; font-weight: bold;">$</span> <span style="color: #06c; font-weight: bold;">do</span> 
  <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="background-color: #3cb371;">&quot;Bye&quot;</span> 
  mainQuit 
  onDestroy window mainQuit 
  widgetShowAll window 
  mainGUI</pre></td></tr></table></div>

<p>Et voilà. Assez simple non ? <img src='http://www.coder-studio.com/blog/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' /> </p>
]]></content:encoded>
			<wfw:commentRss>http://www.coder-studio.com/blog/gtk-en-haskell/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
		</item>
		<item>
		<title>Récupération et parsing d&#8217;un flux Atom XML en Haskell</title>
		<link>http://www.coder-studio.com/blog/recuperation-et-parsing-dun-flux-atom-xml-en-haskell/</link>
		<comments>http://www.coder-studio.com/blog/recuperation-et-parsing-dun-flux-atom-xml-en-haskell/#comments</comments>
		<pubDate>Mon, 04 May 2009 20:27:26 +0000</pubDate>
		<dc:creator>Alp Mestan</dc:creator>
				<category><![CDATA[Langages fonctionnels]]></category>
		<category><![CDATA[atom]]></category>
		<category><![CDATA[download]]></category>
		<category><![CDATA[feed]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[xml]]></category>

		<guid isPermaLink="false">http://www.coder-studio.com/blog/?p=301</guid>
		<description><![CDATA[Bonsoir,
Il y a peu, on m&#8217;a demandé d&#8217;écrire un programme qui récupère un flux Atom XML et qui ne récupère que le titre et l&#8217;url des éléments (qui en l&#8217;occurence sont des billets aggrégés sur Planet OCaml).
J&#8217;ai hésité entre OCaml, C++ et Haskell. Plutôt tenté par du fonctionnel, mon choix s&#8217;est vite porté sur Haskell [...]]]></description>
			<content:encoded><![CDATA[<p>Bonsoir,</p>
<p>Il y a peu, on m&#8217;a demandé d&#8217;écrire un programme qui récupère un flux Atom XML et qui ne récupère que le titre et l&#8217;url des éléments (qui en l&#8217;occurence sont des billets aggrégés sur <a href="http://planet.ocamlcore.org/">Planet OCaml</a>).</p>
<p>J&#8217;ai hésité entre OCaml, C++ et Haskell. Plutôt tenté par du fonctionnel, mon choix s&#8217;est vite porté sur Haskell grâce au nombre impressionnant de paquets présents sur Hackage.<br />
J&#8217;ai donc opté pour le paquet <a href="http://hackage.haskell.org/cgi-bin/hackage-scripts/package/feed-0.3.6">feed</a> pour la gestion d&#8217;Atom et <a href="http://hackage.haskell.org/cgi-bin/hackage-scripts/package/download">download</a> pour la récupération du XML distant, qui se situe <a href="http://planet.ocamlcore.org/atom.xml">ici</a>).</p>
<div class="wp-caption aligncenter" style="width: 70px"><img alt="Haskell Logo" src="http://haskell.org/sitewiki/images/a/a8/Haskell-logo-60.png" title="Haskell Logo" width="60" height="43" /><p class="wp-caption-text">Haskell Logo</p></div>
<p><span id="more-301"></span></p>
<p>Alors, voyons voir&#8230; Premièrement, on importe les modules dont on a besoin, évidemment.</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code29'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30129"><td class="code" id="p301code29"><pre class="haskell" style="font-family:monospace;"><span style="color: #06c; font-weight: bold;">import</span> Network<span style="color: #339933; font-weight: bold;">.</span>Download
<span style="color: #06c; font-weight: bold;">import</span> Text<span style="color: #339933; font-weight: bold;">.</span>Atom<span style="color: #339933; font-weight: bold;">.</span>Feed
<span style="color: #06c; font-weight: bold;">import</span> Text<span style="color: #339933; font-weight: bold;">.</span>Feed<span style="color: #339933; font-weight: bold;">.</span>Import
<span style="color: #06c; font-weight: bold;">import</span> Text<span style="color: #339933; font-weight: bold;">.</span>Feed<span style="color: #339933; font-weight: bold;">.</span>Types</pre></td></tr></table></div>

<p>Ensuite, on définit l&#8217;adresse du fichier atom.xml&#8230; Toujours rien de bien sorcier.</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code30'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30130"><td class="code" id="p301code30"><pre class="haskell" style="font-family:monospace;">url <span style="color: #339933; font-weight: bold;">=</span> <span style="background-color: #3cb371;">&quot;http://planet.ocamlcore.org/atom.xml&quot;</span></pre></td></tr></table></div>

<p>Puis on se lance dans main !</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code31'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30131"><td class="code" id="p301code31"><pre class="haskell" style="font-family:monospace;">main <span style="color: #339933; font-weight: bold;">=</span> <span style="color: #06c; font-weight: bold;">do</span>
    <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="background-color: #3cb371;">&quot;*** Recent blog posts ***&quot;</span>
    Right src <span style="color: #339933; font-weight: bold;">&lt;-</span> openURIString url</pre></td></tr></table></div>

<p>Ici, on affiche simplement un message dans la console, puis on récupère le contenu du fichier dans la chaîne de caractères <em>src</em>.<br />
<strong>Right</strong> est l&#8217;un des constructeurs du type <a href="http://hackage.haskell.org/packages/archive/base/4.1.0.0/doc/html/Data-Either.html#t%3AEither"><strong>Either</strong></a>, ne vous en préoccupez pas trop.</p>
<p>Ensuite, on s&#8217;occupe à proprement parler du flux Atom&#8230;</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code32'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30132"><td class="code" id="p301code32"><pre class="haskell" style="font-family:monospace;"><span style="color: #06c; font-weight: bold;">let</span> Just <span style="color: green;">&#40;</span>AtomFeed is<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">=</span> parseFeedString src</pre></td></tr></table></div>

<p><strong>Just</strong> est un constructeur du type <a href="http://hackage.haskell.org/packages/archive/base/4.1.0.0/doc/html/Data-Maybe.html#t%3AMaybe"><strong>Maybe</strong></a>, qui permet de gérer les erreurs (Just mavaleur si pas eu d&#8217;erreur, Nothing si une erreur). AtomFeed est lui un constructeur pour le type <a href="http://hackage.haskell.org/packages/archive/feed/0.3.6/doc/html/Text-Feed-Types.html#t%3AFeed"><strong>Feed</strong></a> précisant que c&#8217;est un flux Atom, et non RSS1 ou RSS2 par exemple (qui sont eux aussi gérés par ce même paquet). La fonction <em>parseFeedString</em> prend donc une chaîne (ici <em>src</em>) et retourne un flux Atom&#8230; C&#8217;est là, en utilisant <em>is</em>, que l&#8217;on va pouvoir récupérer les différents éléments du XML au format Atom.</p>
<p>Bon, et si on récupérait les différentes entrées de notre flux (ici ce sont des billets de blog) ?</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code33'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30133"><td class="code" id="p301code33"><pre class="haskell" style="font-family:monospace;"><span style="color: #06c; font-weight: bold;">let</span> entries <span style="color: #339933; font-weight: bold;">=</span> feedEntries is</pre></td></tr></table></div>

<p>Ceci nous retourne donc une liste d&#8217;<a href="http://hackage.haskell.org/packages/archive/feed/0.3.6/doc/html/Text-Atom-Feed.html#t%3AEntry"><strong>Entry</strong></a>. Et c&#8217;est parti, on va récupérer les informations qu&#8217;il nous faut, puis les afficher !</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code34'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30134"><td class="code" id="p301code34"><pre class="haskell" style="font-family:monospace;"><span style="color: #06c; font-weight: bold;">let</span> infos <span style="color: #339933; font-weight: bold;">=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:map"><span style="font-weight: bold;">map</span></a> <span style="color: green;">&#40;</span>\e <span style="color: #339933; font-weight: bold;">-&gt;</span> <span style="color: green;">&#40;</span>entryTitle e<span style="color: #339933; font-weight: bold;">,</span> entryId e<span style="color: green;">&#41;</span><span style="color: green;">&#41;</span> entries
<a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:mapM_"><span style="font-weight: bold;">mapM_</span></a> <span style="color: green;">&#40;</span>\<span style="color: green;">&#40;</span>x<span style="color: #339933; font-weight: bold;">,</span>y<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="color: #339933; font-weight: bold;">$</span> <span style="color: green;">&#40;</span>stringize x<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">++</span> <span style="background-color: #3cb371;">&quot;: &quot;</span> <span style="color: #339933; font-weight: bold;">++</span> y<span style="color: green;">&#41;</span> infos</pre></td></tr></table></div>

<p>Oui, oui, ça se complique un peu.<br />
Tout d&#8217;abord, qu&#8217;est-ce que <em>infos</em> ? <em>map</em> transforme chaque élément en l&#8217;image de l&#8217;élément donné par son premier argument, qui est donc une fonction. Ici, on va transformer chaque <strong>Entry</strong> en un couple <em>(titre, id)</em> associé à notre entrée, où id se trouve être l&#8217;URL originale du billet.<br />
Bon infos est donc la liste des couples (titre, url). Ah ? Ce n&#8217;étant pas tellement cette ligne qui vous faisait peur mais la suivante ?<br />
Bon, sans rentrer en détail dans les monades (<a href="http://haskell.org/haskellwiki/Monad">la page Monad du HaskellWiki</a> le faisant mieux que moi, et surtout donnant d&#8217;excellents liens pour comprendre de quoi il s&#8217;agit, où c&#8217;est utilisé, etc), on se trouve dans la monade IO. mapM_ se retrouve donc avec le type :</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code35'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30135"><td class="code" id="p301code35"><pre class="haskell" style="font-family:monospace;"><span style="color: green;">&#40;</span>a <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> b<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">-&gt;</span> <span style="color: green;">&#91;</span>a<span style="color: green;">&#93;</span> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:IO"><span style="color: #cccc00; font-weight: bold;">IO</span></a> <span style="color: green;">&#40;</span><span style="color: green;">&#41;</span></pre></td></tr></table></div>

<p>Notre <em>[a]</em>, c&#8217;est infos, donc notre liste de couples&#8230;<br />
<em>(a -> IO b)</em> est effectivement le type de notre fonction anonyme, que je me permets de vous montrer à part ici :</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code36'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30136"><td class="code" id="p301code36"><pre class="haskell" style="font-family:monospace;">\<span style="color: green;">&#40;</span>x<span style="color: #339933; font-weight: bold;">,</span>y<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="color: #339933; font-weight: bold;">$</span> <span style="color: green;">&#40;</span>stringize x<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">++</span> <span style="background-color: #3cb371;">&quot;: &quot;</span> <span style="color: #339933; font-weight: bold;">++</span> y</pre></td></tr></table></div>

<p>A un couple (titre,url), elle associe un appel à <em>putStrLn</em>, qui retourne <em>IO ()</em>. Donc le type <em>b</em> est en fait <em>()</em>. <em>mapM_</em> ne faut qu&#8217;effectuer des actions dans une monade donnée, en ignorant le résultat de chacune au lieu de les placer des une liste comme le fait son homologue <em>mapM</em></p>
<p>Ah oui, j&#8217;oubliais, stringize, qui est définie juste après fonction main.</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code37'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30137"><td class="code" id="p301code37"><pre class="haskell" style="font-family:monospace;">stringize <span style="color: #339933; font-weight: bold;">::</span> TextContent <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a>
stringize <span style="color: green;">&#40;</span>TextString s<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">=</span> s
stringize <span style="color: #339933; font-weight: bold;">_</span> <span style="color: #339933; font-weight: bold;">=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:error"><span style="font-weight: bold;">error</span></a> <span style="background-color: #3cb371;">&quot;shoud not be called on something else than TextString&quot;</span></pre></td></tr></table></div>

<p>Elle me permet juste de passer d&#8217;une valeur construite avec TextString, donc de type <a href="http://hackage.haskell.org/packages/archive/feed/0.3.6/doc/html/Text-Atom-Feed.html#t%3ATextContent"><strong>TextContent</strong></a>, à la valeur qui est en fait englobée par ce type, de type String.</p>
<p>Voilà donc le code complet :</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p301code38'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p30138"><td class="code" id="p301code38"><pre class="haskell" style="font-family:monospace;"><span style="color: #06c; font-weight: bold;">import</span> Network<span style="color: #339933; font-weight: bold;">.</span>Download
<span style="color: #06c; font-weight: bold;">import</span> Text<span style="color: #339933; font-weight: bold;">.</span>Atom<span style="color: #339933; font-weight: bold;">.</span>Feed
<span style="color: #06c; font-weight: bold;">import</span> Text<span style="color: #339933; font-weight: bold;">.</span>Feed<span style="color: #339933; font-weight: bold;">.</span>Import
<span style="color: #06c; font-weight: bold;">import</span> Text<span style="color: #339933; font-weight: bold;">.</span>Feed<span style="color: #339933; font-weight: bold;">.</span>Types
&nbsp;
url <span style="color: #339933; font-weight: bold;">=</span> <span style="background-color: #3cb371;">&quot;http://planet.ocamlcore.org/atom.xml&quot;</span>
&nbsp;
main <span style="color: #339933; font-weight: bold;">=</span> <span style="color: #06c; font-weight: bold;">do</span>
    <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="background-color: #3cb371;">&quot;*** Recent blog posts ***&quot;</span>
    Right src <span style="color: #339933; font-weight: bold;">&lt;-</span> openURIString url
    <span style="color: #06c; font-weight: bold;">let</span> Just <span style="color: green;">&#40;</span>AtomFeed is<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">=</span> parseFeedString src
    <span style="color: #06c; font-weight: bold;">let</span> entries <span style="color: #339933; font-weight: bold;">=</span> feedEntries is
    <span style="color: #06c; font-weight: bold;">let</span> infos <span style="color: #339933; font-weight: bold;">=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:map"><span style="font-weight: bold;">map</span></a> <span style="color: green;">&#40;</span>\e <span style="color: #339933; font-weight: bold;">-&gt;</span> <span style="color: green;">&#40;</span>entryTitle e<span style="color: #339933; font-weight: bold;">,</span> entryId e<span style="color: green;">&#41;</span><span style="color: green;">&#41;</span> entries
    <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:mapM_"><span style="font-weight: bold;">mapM_</span></a> <span style="color: green;">&#40;</span>\<span style="color: green;">&#40;</span>x<span style="color: #339933; font-weight: bold;">,</span>y<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:putStrLn"><span style="font-weight: bold;">putStrLn</span></a> <span style="color: #339933; font-weight: bold;">$</span> <span style="color: green;">&#40;</span>stringize x<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">++</span> <span style="background-color: #3cb371;">&quot;: &quot;</span> <span style="color: #339933; font-weight: bold;">++</span> y<span style="color: green;">&#41;</span> infos
&nbsp;
stringize <span style="color: #339933; font-weight: bold;">::</span> TextContent <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a>
stringize <span style="color: green;">&#40;</span>TextString s<span style="color: green;">&#41;</span> <span style="color: #339933; font-weight: bold;">=</span> s
stringize <span style="color: #339933; font-weight: bold;">_</span> <span style="color: #339933; font-weight: bold;">=</span> <span style="background-color: #3cb371;">&quot;stringize Error&quot;</span></pre></td></tr></table></div>

<p>La compilation :</p>
<blockquote><p>$ ghc -package download -o cwn cwn.hs</p></blockquote>
<p>Et un exemple d&#8217;execution :</p>
<blockquote><p>$ ./cwn<br />
*** Recent blog posts ***<br />
ocaml-text: http://forge.ocamlcore.org/projects/ocaml-text/<br />
0.1.3 sources now in subversion: http://forge.ocamlcore.org/forum/forum.php?forum_id=355<br />
Sudoku in ocamljs, part 2: RPC over HTTP: tag:blogger.com,1999:blog-1445545651031573301.post-3490486535879812384<br />
Caml Weekly News, 28 Apr 2009: http://alan.petitepomme.net/cwn/2009.04.28.html<br />
Bouncing Ball in OCaml with OCamlSDL: http://blog.mestan.fr/?p=31<br />
Sudoku in ocamljs, part 1: DOM programming: tag:blogger.com,1999:blog-1445545651031573301.post-4574121943207730951<br />
Using OCaml’s module functors to provide monadic contexts for Batteries: http://blog.mestan.fr/?p=30<br />
Lastfm no longer free as in free beer (and some bits about xml in OCaml): http://blog.rastageeks.org/spip.php?article34<br />
Last lecture: http://dutherenverseauborddelatable.wordpress.com/?p=571<br />
Liquidsoap now supports AAC+ encoding.: http://blog.rastageeks.org/spip.php?article33</p></blockquote>
<p>Alors, pas si &laquo;&nbsp;académique&nbsp;&raquo; que ça le fonctionnel, non ? <img src='http://www.coder-studio.com/blog/wp-includes/images/smilies/icon_wink.gif' alt=';)' class='wp-smiley' /><br />
Tout ça en 18 lignes, lignes vides comprises, 15 non comprises.</p>
<p>Enjoy.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.coder-studio.com/blog/recuperation-et-parsing-dun-flux-atom-xml-en-haskell/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>La programmation fonctionnelle n&#8217;est pas un jouet pour académiciens</title>
		<link>http://www.coder-studio.com/blog/la-programmation-fonctionnelle-nest-pas-un-jouet-pour-academiciens/</link>
		<comments>http://www.coder-studio.com/blog/la-programmation-fonctionnelle-nest-pas-un-jouet-pour-academiciens/#comments</comments>
		<pubDate>Sun, 26 Apr 2009 18:30:26 +0000</pubDate>
		<dc:creator>Alp Mestan</dc:creator>
				<category><![CDATA[Langages fonctionnels]]></category>
		<category><![CDATA[Non classé]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[lambda]]></category>
		<category><![CDATA[lisp]]></category>
		<category><![CDATA[ocaml]]></category>
		<category><![CDATA[programmation fonctionnelle]]></category>

		<guid isPermaLink="false">http://www.coder-studio.com/blog/?p=267</guid>
		<description><![CDATA[Bonjour,
Cela fait maintenant un moment que j&#8217;apprends et pratique la programmation fonctionnelle, aussi bien sur le point de vue théorique en m&#8217;intéressant à ses relations avec la théorie des catégories (mathématiques) entre autres, que sur le point de vue pratique, c&#8217;est à dire que j&#8217;ai mené quelques projets (de petite envergure&#8230; oui, c&#8217;est proportionnel au [...]]]></description>
			<content:encoded><![CDATA[<p>Bonjour,</p>
<p>Cela fait maintenant un moment que j&#8217;apprends et pratique la programmation fonctionnelle, aussi bien sur le point de vue théorique en m&#8217;intéressant à ses relations avec la théorie des catégories (mathématiques) entre autres, que sur le point de vue pratique, c&#8217;est à dire que j&#8217;ai mené quelques projets (de petite envergure&#8230; oui, c&#8217;est proportionnel au temps que je peux passer dessus) à bien.</p>
<p>Quand on dit &laquo;&nbsp;langage fonctionnel&nbsp;&raquo; ou &laquo;&nbsp;programmation fonctionnelle&nbsp;&raquo;, les gens s&#8217;imaginent (pour ceux qui ne connaissent pas) des programmes avec tout un tas de fonctions, c&#8217;est tout. Ce n&#8217;est pas ça la programmation fonctionnelle. Enfin biensûr il y a des fonctions, mais la programmation fonctionnelle ne s&#8217;arrête pas là.</p>
<p>Déjà, la programmation fonctionnelle, c&#8217;est une toute autre façon de concevoir des programmes. Détailler toutes les différences avec la programmation impérative serait pire que les 12 travaux d&#8217;Hercules et c&#8217;est pourquoi je ne le ferai pas. Je vais toutefois vous parler des points qui font que je suis désormais adepte de ce style de programmation.</p>
<p><center><img src="http://www.geocities.com/EnchantedForest/1110/images/lambda.gif" alt="" title="La programmation fonctionnelle tire ses racines du lambda-calcul" /></center><br />
<span id="more-267"></span></p>
<p>Tout d&#8217;abord, étant assez orienté mathématiques, il y a une première chose qui me plaît. Dans les langages de programmation fonctionnelle (du moins la plupart), on définit des types, des opérations sur ces types, le tout très simplement et de manière on ne peut plus cohérente.</p>
<p>Ensuite, pour les langages fonctionnels compilés et typés statiquement, on est généralement accompagné d&#8217;un compilateur très strict, qui tentera d&#8217;éliminer un maximum d&#8217;incohérences (comprendre &laquo;&nbsp;erreurs&nbsp;&raquo;) en nous envoyant des erreurs très précises en rapport avec le fait que nous n&#8217;avons pas bien typé des parties de notre programme. De plus, les 3 langages majeurs pour une utilisation &laquo;&nbsp;real world&nbsp;&raquo;, Haskell, OCaml et F#, ont vu leur compilateur se doter de l&#8217;inférence de type ; il s&#8217;agit de la capacité qu&#8217;a un compilateur a donner lui-même un type à vos valeurs dans le programme (fonctions, expressions, &#8230;). Entre ceci et la vérification des types, la compilation possède une part de travail autour des types en action dans votre code.</p>
<p>De plus, en programmation fonctionnelle, il s&#8217;agit de ne pas avoir ce que l&#8217;on appelle des effets de bords ; on parle de programmation fonctionnelle pure ; dans un tel cadre, une fonction à qui l&#8217;on donne les mêmes entrées renverra toujours la même sortie. Les programmeurs fonctionnels font en sorte d&#8217;isoler les parties pour lesquelles ce n&#8217;est pas vrai (lecture d&#8217;un fichier, intéraction réseau, &#8230;) : monades en Haskell, on laisse la possibilité de faire de l&#8217;impératif pour OCaml et F#, &#8230; </p>
<p>Continuons sur la curryfication. Cette dernière consiste à faire par exemple d&#8217;une fonction de 2 arguments 2 fonctions à 1 argument, qui pourront s&#8217;appliquer partiellement. Si l&#8217;on définit une fonction &laquo;&nbsp;add&nbsp;&raquo; pour ajouter 2 nombres x et y, alors on pourra appliquer add à son premier argument, x, en lui donnant par exemple la valeur 12, pour obtenir une fonction à UN SEUL argument qui additionnera son argument à 12.</p>
<p>Les fonctions sont capitales en programmation fonctionnelle. Contrairement à dans un certain nombre de langages (beaucoup), les fonctions peuvent être stockées, passées en argument, construites à la volée, retournées par d&#8217;autres fonctions, etc. Elles deviennent des valeurs de première classe. </p>
<p>A propos du passage en argument, une chose très importante en programmation fonctionnelle est la possibilité d&#8217;abstraire une partie des algorithmes et d&#8217;en confier la responsabilité à une fonction donnée en argument par exemple. Une fonction qui prend une autre fonction en argument est appelée &laquo;&nbsp;fonction d&#8217;ordre supérieur&nbsp;&raquo;. Cela permet de factoriser un maximum de code tout en laissant la variabilité possible grâce au passage de fonction en argument. Le compilateur fera les vérifications nécessaires pour voir si les types concordent, ne vous inquiétez pas.</p>
<p>La paresse est également quelque chose qui s&#8217;avère bien sympathique parfois. Il s&#8217;agit de n&#8217;évaluer une expression qu&#8217;au moment où l&#8217;on en aura besoin (affichage du résultat de l&#8217;évaluation de l&#8217;expression &#8212; comme une addition &#8212; par exemple). Elle est mise en oeuvre différemment selon les langages (implicitement en Haskell, c&#8217;est le compilateur qui gère cela, alors que c&#8217;est explicit en OCaml &#8212; module Lazy).</p>
<p>Tout cela, rajouté aux syntaxes assez simples, donne une très grande expressivité aux langages fonctionnels, proche de l&#8217;expressivité que l&#8217;on a en mathématiques. Qui plus est, rappelons-le, les langages fonctionnels sont des langages dits &laquo;&nbsp;déclaratifs&nbsp;&raquo;. On exprime le problème, on obtient la solution, contrairement à ce que l&#8217;on fait dans un langage impératif où l&#8217;on doit donner toutes les étapes à la main nous-mêmes.</p>
<p>Bref, beaucoup d&#8217;avantages, un tout nouveau style de programmation, cela ne vaut-il pas le détour ? Allez, si vous voulez en savoir plus, voici quelques liens essentiels pour terminer ce billet sur la programmation fonctionnelle.<br />
<a href="http://damien-guichard.developpez.com/tutoriels/ocaml/">Cours d&#8217;introduction à OCaml de Damien Guichard</a> &#8212; dont je me suis beaucoup servi et que j&#8217;apprécie beaucoup<br />
<a href="http://gorgonite.developpez.com/livres/traductions/haskell/gentle-haskell/">Traduction de &laquo;&nbsp;A gentle introduction to Haskell&nbsp;&raquo;</a> &#8212; un peu rude pour débuter, mais vous fera comprendre pas mal de choses. </p>
<p>N&#8217;hésitez pas à utiliser le forum pour donner vos avis et retours d&#8217;expérience ou pour des questions, bien évidemment !</p>
]]></content:encoded>
			<wfw:commentRss>http://www.coder-studio.com/blog/la-programmation-fonctionnelle-nest-pas-un-jouet-pour-academiciens/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Supprimer toutes les instances d&#8217;un caractère dans une chaîne en Haskell</title>
		<link>http://www.coder-studio.com/blog/supprimer-toutes-les-instances-dun-caractere-dans-une-chaine-en-haskell/</link>
		<comments>http://www.coder-studio.com/blog/supprimer-toutes-les-instances-dun-caractere-dans-une-chaine-en-haskell/#comments</comments>
		<pubDate>Fri, 27 Feb 2009 08:10:17 +0000</pubDate>
		<dc:creator>Alp Mestan</dc:creator>
				<category><![CDATA[Langages fonctionnels]]></category>
		<category><![CDATA[caractères]]></category>
		<category><![CDATA[chaînes]]></category>
		<category><![CDATA[fonctionnel]]></category>
		<category><![CDATA[haskell]]></category>

		<guid isPermaLink="false">http://r19649.ovh.net/cs/blog/?p=80</guid>
		<description><![CDATA[Bonjour,
J&#8217;inaugure mon compte sur ce blog en y postant mon premier billet, sur Haskell qui plus est !
Je vais vous montrer puis vous expliquer un moyen simple de supprimer toutes les instances d&#8217;un caractère donné dans une chaîne, en Haskell&#8230; en une ligne, oui.
Il s&#8217;agit donc par exemple de pouvoir supprimer tous les &#8216;a&#8217; dans [...]]]></description>
			<content:encoded><![CDATA[<p>Bonjour,</p>
<p>J&#8217;inaugure mon compte sur ce blog en y postant mon premier billet, sur Haskell qui plus est !</p>
<p>Je vais vous montrer puis vous expliquer un moyen simple de supprimer toutes les instances d&#8217;un caractère donné dans une chaîne, en Haskell&#8230; en une ligne, oui.<br />
Il s&#8217;agit donc par exemple de pouvoir supprimer tous les &#8216;a&#8217; dans (je vais faire dans l&#8217;original) le titre de ce billet !</p>
<p>&laquo;&nbsp;Supprimer toutes les instances d&#8217;un caractère dans une chaîne en Haskell&nbsp;&raquo;<br />
doit donc devenir :<br />
&laquo;&nbsp;Supprimer toutes les instnces d&#8217;un crctère dns une chîne en Hskell&nbsp;&raquo;</p>
<p><span id="more-80"></span></p>
<p>Voici comment faire, en utilisant la fonction filter que nous expliquerons plus bas.</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p80code44'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p8044"><td class="code" id="p80code44"><pre class="haskell" style="font-family:monospace;">strip <span style="color: #339933; font-weight: bold;">::</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:Char"><span style="color: #cccc00; font-weight: bold;">Char</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a>
strip c s <span style="color: #339933; font-weight: bold;">=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:filter"><span style="font-weight: bold;">filter</span></a> <span style="color: green;">&#40;</span><span style="color: #339933; font-weight: bold;">/=</span> c<span style="color: green;">&#41;</span> s</pre></td></tr></table></div>

<p>Premièrement, regardons le type de cette fonction.<br />
Elle prend a deux arguments : un caractère et une chaîne de caractères (qui, en Haskell, est définie comme une liste de caractères <em>[Char]</em>). Elle retourne une chaîne de caractères ; c&#8217;est bien ce que l&#8217;on désire.</p>
<p>Regardons ensuite la seconde ligne : <em>c</em> désigne le fameux caractère à supprimer et <em>s</em> la chaîne dans laquelle le supprimer.</p>
<p>Nous faisons ensuite appel à la fonction filter qui prend un prédicat à un argument (une fonction d&#8217;un argument qui retourne un booléen) et qui s&#8217;applique ensuite sur une liste, donnée en second argument. Elle retourne une liste où seuls les éléments vérifiant le prédicat sont restés. Je tiens à rappeler que Haskell étant un langage fonctionnel, on ne modifie pas la liste, on en retourne une nouvelle. N&#8217;ayez crainte, ça ne va pas faire des programme lourd, il y a de belles optimisations qui tournent derrière.</p>
<p>Mettez le code précédent dans un fichier strip.hs par exemple, et chargez-le dans GHCi via <em>:load strip.hs</em> (en vous assurant que vous êtes dans le bon répertoire). Puis testons :</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p80code45'); return false;">View Code</a> PRELUDE</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p8045"><td class="code" id="p80code45"><pre class="prelude" style="font-family:monospace;">*Main&gt; strip 'a' &quot;Supprimer toutes les instances d'un caractères dans une chaîne en Haskell&quot;
&quot;Supprimer toutes les instnces d'un crctères dns une chîne en Hskell&quot;</pre></td></tr></table></div>

<p>Notons toutefois que le code ci-dessus peut-être encore plus court !<br />
En effet, nous avons indiqué la chaine &laquo;&nbsp;s&nbsp;&raquo; alors que l&#8217;on peut s&#8217;en passer et écrire cela :</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p80code46'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p8046"><td class="code" id="p80code46"><pre class="haskell" style="font-family:monospace;">strip <span style="color: #339933; font-weight: bold;">::</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:Char"><span style="color: #cccc00; font-weight: bold;">Char</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a>
strip c <span style="color: #339933; font-weight: bold;">=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:filter"><span style="font-weight: bold;">filter</span></a> <span style="color: green;">&#40;</span><span style="color: #339933; font-weight: bold;">/=</span> c<span style="color: green;">&#41;</span></pre></td></tr></table></div>

<p>Et encore, on sent que strip n&#8217;est définissable qu&#8217;avec filter et l&#8217;opérateur /= &#8230; Et bien tout à fait !</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p80code47'); return false;">View Code</a> HASKELL</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p8047"><td class="code" id="p80code47"><pre class="haskell" style="font-family:monospace;">strip <span style="color: #339933; font-weight: bold;">::</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:Char"><span style="color: #cccc00; font-weight: bold;">Char</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a> <span style="color: #339933; font-weight: bold;">-&gt;</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#t:String"><span style="color: #cccc00; font-weight: bold;">String</span></a>
strip <span style="color: #339933; font-weight: bold;">=</span> <a href="http://haskell.org/ghc/docs/latest/html/libraries/base/Prelude.html#v:filter"><span style="font-weight: bold;">filter</span></a> <span style="color: #339933; font-weight: bold;">.</span> <span style="color: green;">&#40;</span><span style="color: #339933; font-weight: bold;">/=</span><span style="color: green;">&#41;</span></pre></td></tr></table></div>

<p>Cette propriété se nomme <strong>êta-réduction</strong> et rend le code bien plus sobre, concis et clair. En effet, en Haskell, après un certain temps, on parvient à écrire du code qui n&#8217;est presque qu&#8217;un enchainement de compositions de fonctions, de sorte qu&#8217;une ligne ne soit presque qu&#8217;une phrase, si l&#8217;on nomme bien les fonctions. </p>
<p>Je rappelle que le &#8216;.&#8217; est tout simplement l&#8217;opérateur de composition de fonctions, et il suffit de regarder son type pour s&#8217;en convaincre :<br />
Tapez <em>:t (.)</em> dans GHCi pour vous en convaincre, il vous dira ceci :</p>

<div class="wp_codebox_msgheader"><span class="right"><sup><a href="http://www.ericbess.com/ericblog/2008/03/03/wp-codebox/#examples" target="_blank" title="WP-CodeBox HowTo?"><span style="color: #99cc00">?</span></a></sup></span><span class="left"><a href="javascript:;" onclick="javascript:showCodeTxt('p80code48'); return false;">View Code</a> PRELUDE</span><div class="codebox_clear"></div></div><div class="wp_codebox"><table><tr id="p8048"><td class="code" id="p80code48"><pre class="prelude" style="font-family:monospace;">*Main&gt; :t (.)
(.) :: (b -&gt; c) -&gt; (a -&gt; b) -&gt; a -&gt; c</pre></td></tr></table></div>

<p>Ce qui signifie en gros : </p>
<blockquote><p>Pour tous types a, b et c (<em>polymorphisme inside</em>), l&#8217;opérateur <em>.</em> prend deux fonctions, l&#8217;une (disons g) du type b vers le type c, l&#8217;autre (disons f) du type a vers le type b, et elle en fait la composition pour obtenir une fonction qui va du type a vers le type c.</p></blockquote>
<p>C&#8217;est exactement ce que fait l&#8217;opérateur &#8216;<em>o</em>&#8216; en Mathématiques ; en effet, <em>g . f</em> en Haskell est équivalent à <em>g o f</em> en Mathématiques.</p>
<p>Voilà pour mon premier billet ici. </p>
<p>Si vous avez découvert Haskell par ce billet et que vous souhaitez vous y mettre, voici quelques liens essentiels :<br />
<a href="http://www.haskell.org/">http://www.haskell.org/</a> : Site officiel, où l&#8217;on peut télécharger compilateur, interpréteur, outils &#038; bibliothèques divers et variés mais également consulter des tutoriels/cours sur Haskell  &#8211; c&#8217;est le QG de tous les programmeurs Haskell<br />
<a href="http://en.wikibooks.org/wiki/Haskell">http://en.wikibooks.org/wiki/Haskell</a> : Le Wikibook sur Haskell<br />
<a href="http://book.realworldhaskell.org/read/">http://book.realworldhaskell.org/read/</a> : Le livre &#8216;Real World Haskell&#8217; qui est disponible gratuitement en lecture en ligne<br />
Et pour terminer, il y a le salon #haskell (et #haskell.fr, mais ce dernier est peu actif) sur le réseau IRC Freenode.</p>
<p>A bientôt !</p>
]]></content:encoded>
			<wfw:commentRss>http://www.coder-studio.com/blog/supprimer-toutes-les-instances-dun-caractere-dans-une-chaine-en-haskell/feed/</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
	</channel>
</rss>
