<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Strict//EN" "http://www.w3.org/TR/xhtml1/DTD/xhtml1-strict.dtd">
<html xmlns="http://www.w3.org/1999/xhtml" lang="en" xml:lang="en"> 
<head>
<title>Accessing files</title>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<meta name="generator" content="pandoc" />
<link rel="shortcut icon" href="icon.ico" />
<script src="common_en.js" charset="utf-8" type="text/javascript"></script> 
<link rel="stylesheet" href="common.css" type="text/css" />
</head>
<body onload="javascript:resetForms(); javascript:slidy_init();">
<div><h1 class="cover">Accessing files</h1>
<div id="info"></div>
<ul>
<li><a href="#accessing-files">Accessing files</a><ul>
<li><a href="#sorting-data">Sorting data</a></li>
<li><a href="#pure-code">Pure code</a></li>
<li><a href="#doing-io">Doing I/O</a></li>
</ul></li>
</ul>
</div>
<section id="accessing-files" class="level1">
<h1>Accessing files</h1>
<p>To perform any kind of input or output (to the screen, to a file, to the network, etc), your Haskell program must use <code>IO</code> monad. Typically, a Haskell program begins with its <code>main</code> function, which has this type signature:</p>
<pre><code>main :: IO ()</code></pre>
<p>Because main is <code>IO</code>-monadic, it can call other <code>IO</code>-monadic functions as well as non-monadic (<em>pure</em>) functions. Pure functions can call other pure functions, but not <code>IO</code>-monadic functions (unless they cheat).</p>
<section id="sorting-data" class="level2">
<h2>Sorting data</h2>
<p>Ultimately, we want to sort the contents of a file that contains columns of data. For example, imagine if the file looks like this:</p>
<pre><code>Jako   23    99
Eva    42    5000
Katka  0     2</code></pre>
<p>Here there are three columns. We want to write a program that can read the file, sort by any of the columns, and output a sorted file.</p>
</section>
<section id="pure-code" class="level2">
<h2>Pure code</h2>
<p>First, let’s write some pure functions for manipulating data.</p>
<p>The <code>columnize</code> function should take the lines of the file, as a list of strings, and break it into a list of a list of columns.</p>
<div class="sourceCode" id="cb3"><pre class="sourceCode haskell"><code class="sourceCode haskell"><a class="sourceLine" id="cb3-1" data-line-number="1"><span class="ot">columnize ::</span> [<span class="dt">String</span>] <span class="ot">-&gt;</span> [[<span class="dt">String</span>]]</a></code></pre></div>
<div class="indent"><form class="interpreter" action="javascript:getOne('c=check&amp;f=FL_Files_en_68993d5b01c4a27be6aa0ff0904acfaf.hs','68993d5b01c4a27be6aa0ff0904acfaf','68993d5b01c4a27be6aa0ff0904acfaf');"><textarea cols="80" rows="3" id="tarea68993d5b01c4a27be6aa0ff0904acfaf"></textarea><br /><input type="submit" value="Check" /></form><div class="answer" id="res68993d5b01c4a27be6aa0ff0904acfaf"></div></div>
<form class="resetinterpreter" action="javascript:getOne('c=eval&amp;f=FL_Files_en.hs','121ffdcacf0a71b277080faa32d211cf','121ffdcacf0a71b277080faa32d211cf');"><code class="prompt">Test&gt; </code><input class="interpreter" type="text" size="80" id="tarea121ffdcacf0a71b277080faa32d211cf" value="columnize [&quot;Jako   23    99&quot;,&quot;Eva    42    5000&quot;,&quot;Katka  0     2&quot;]" /><br /><div class="answer" id="res121ffdcacf0a71b277080faa32d211cf"><code class="result">[[&quot;Jako&quot;, &quot;23&quot;, &quot;99&quot;], [&quot;Eva&quot;, &quot;42&quot;, &quot;5000&quot;], [&quot;Katka&quot;, &quot;0&quot;, &quot;2&quot;]]</code><code> :: </code><code class="type">[[String]]</code></div></form>
<p>The <code>flexisort</code> function will take a column number and the columnized file data, and will sort it by that column.</p>
<div class="sourceCode" id="cb4"><pre class="sourceCode haskell"><code class="sourceCode haskell"><a class="sourceLine" id="cb4-1" data-line-number="1"><span class="ot">flexisort ::</span> <span class="dt">Int</span> <span class="ot">-&gt;</span> [[<span class="dt">String</span>]] <span class="ot">-&gt;</span> [[<span class="dt">String</span>]]</a></code></pre></div>
<div class="indent"><form class="interpreter" action="javascript:getOne('c=check&amp;f=FL_Files_en_dbfc808a722f05e4507599bceab686db.hs','dbfc808a722f05e4507599bceab686db','dbfc808a722f05e4507599bceab686db');"><textarea cols="80" rows="3" id="tareadbfc808a722f05e4507599bceab686db"></textarea><br /><input type="submit" value="Check" /></form><div class="answer" id="resdbfc808a722f05e4507599bceab686db"></div></div>
<form class="resetinterpreter" action="javascript:getOne('c=eval&amp;f=FL_Files_en.hs','a717aa18d437fadb61f92a819783bcf4','a717aa18d437fadb61f92a819783bcf4');"><code class="prompt">Test&gt; </code><input class="interpreter" type="text" size="80" id="tareaa717aa18d437fadb61f92a819783bcf4" value="flexisort 0 $ columnize [&quot;Jako   23    99&quot;,&quot;Eva    42    5000&quot;,&quot;Katka  0     2&quot;]" /><br /><div class="answer" id="resa717aa18d437fadb61f92a819783bcf4"><code class="result">[[&quot;Eva&quot;, &quot;42&quot;, &quot;5000&quot;], [&quot;Jako&quot;, &quot;23&quot;, &quot;99&quot;], [&quot;Katka&quot;, &quot;0&quot;, &quot;2&quot;]]</code><code> :: </code><code class="type">[[String]]</code></div></form>
<form class="resetinterpreter" action="javascript:getOne('c=eval&amp;f=FL_Files_en.hs','8ef72160f919636a3dbd06224d1e2ba4','8ef72160f919636a3dbd06224d1e2ba4');"><code class="prompt">Test&gt; </code><input class="interpreter" type="text" size="80" id="tarea8ef72160f919636a3dbd06224d1e2ba4" value="flexisort 1 $ columnize [&quot;Jako   23    99&quot;,&quot;Eva    42    5000&quot;,&quot;Katka  0     2&quot;]" /><br /><div class="answer" id="res8ef72160f919636a3dbd06224d1e2ba4"><code class="result">[[&quot;Katka&quot;, &quot;0&quot;, &quot;2&quot;], [&quot;Jako&quot;, &quot;23&quot;, &quot;99&quot;], [&quot;Eva&quot;, &quot;42&quot;, &quot;5000&quot;]]</code><code> :: </code><code class="type">[[String]]</code></div></form>
<form class="resetinterpreter" action="javascript:getOne('c=eval&amp;f=FL_Files_en.hs','06642b8eaf9d4e54871391a79c8d0015','06642b8eaf9d4e54871391a79c8d0015');"><code class="prompt">Test&gt; </code><input class="interpreter" type="text" size="80" id="tarea06642b8eaf9d4e54871391a79c8d0015" value="flexisort 2 $ columnize [&quot;Jako   23    99&quot;,&quot;Eva    42    5000&quot;,&quot;Katka  0     2&quot;]" /><br /><div class="answer" id="res06642b8eaf9d4e54871391a79c8d0015"><code class="result">[[&quot;Katka&quot;, &quot;0&quot;, &quot;2&quot;], [&quot;Eva&quot;, &quot;42&quot;, &quot;5000&quot;], [&quot;Jako&quot;, &quot;23&quot;, &quot;99&quot;]]</code><code> :: </code><code class="type">[[String]]</code></div></form>
<p>Use the <code>sortBy</code> function in <code>Data.List</code>. Consider the <code>sortBy (compare `on` x)</code> paradigm.</p>
<p>Note that we are sorting by string representation, so in the above example, 5000 is sorted before 99, because <code>&quot;5000&quot; &lt; &quot;99&quot;</code>.</p>
</section>
<section id="doing-io" class="level2">
<h2>Doing I/O</h2>
<p>Write an executable Haskell program (with a <code>main</code> function) named <code>MySort</code> that will do the following:</p>
<ol type="1">
<li>Get two filenames and a column number from its command line. Use <code>System.Environment.getArgs</code> to get the data, and use <code>read</code> to convert the string to an integer.</li>
<li>Read the content of the filename given as the first parameter (using various functions in <code>System.IO</code>).</li>
<li>Sort the lines of that file, using your <code>columnize</code> and <code>flexisort</code> functions.</li>
<li>Write the sorted lines to the filename given as the second parameter.</li>
</ol>
<p>You can compile your program using the <code>ghc</code> command. After you compile it, you should be able to run it like this, assuming there is a textfile named <code>input</code> in the current directory:</p>
<pre><code>./MySort input output 2</code></pre>
<p>Write your program twice: first using Haskell’s monadic bind notation (<code>&gt;&gt;=</code> and <code>&gt;&gt;</code>), then using Haskell’s <code>do</code> notation.</p>
</section>
</section>
</body>
</html>

