<?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>brool</title>
	<atom:link href="http://www.brool.com/index.php/feed" rel="self" type="application/rss+xml" />
	<link>http://www.brool.com</link>
	<description>brool \brool\ (n.) : a low roar; a deep murmur or humming</description>
	<lastBuildDate>Sat, 26 Jun 2010 21:05:13 +0000</lastBuildDate>
	<generator>http://wordpress.org/?v=2.8.4</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
			<item>
		<title>iPhone 4 Notes (And Wireless Problem)</title>
		<link>http://www.brool.com/index.php/iphone-4-notes-and-wireless-problem</link>
		<comments>http://www.brool.com/index.php/iphone-4-notes-and-wireless-problem#comments</comments>
		<pubDate>Sat, 26 Jun 2010 20:59:53 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[reviews]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=431</guid>
		<description><![CDATA[Ended up getting the iPhone 4G &#8212; I had a 3G previously, and it really was starting to show its age &#8212; and it really is a nice phone.  The highlights:

Display is ridiculously nice
It&#8217;s fast &#8212; subjectively, as fast as the iPad &#8212; and the extra CPU power really makes the web browsing much [...]]]></description>
			<content:encoded><![CDATA[<p>Ended up getting the iPhone 4G &mdash; I had a 3G previously, and it really was starting to show its age &mdash; and it really is a nice phone.  The highlights:</p>
<ul>
<li>Display is ridiculously nice</li>
<li>It&#8217;s fast &mdash; subjectively, as fast as the iPad &mdash; and the extra CPU power really makes the web browsing much better.</li>
<li>The bumper case is not that great &mdash; it prevents some headphones from being used (because the distance to the headphone jack is a bit longer) and also prevents you from using the 10,000 iPod USB adapters that you have lying around the house, because the slot in the case for the iPod adapter is just small enough that older adapters don&#8217;t work.  As one of my friends said, &#8220;Get the Dremel!&#8221;</li>
<li>I took the case off and tried to reproduce the reception problems that people had been talking about, but was unable to get it to happen.</li>
</ul>
<p>The ominous thing was that the iPhone 4G suffered from the same wireless problems as the iPad, manifesting as a couple of symptoms: a) unable to connect unless I was really close to the router, b) and really low signal strength.</p>
<h2>Wireless</h2>
<p>I had been living with the wireless problems for a while, although they were extremely frustrating.  Finally, a lucky break meant that I was able figure out the underlying cause (although to my chagrin I discovered later that <a href="http://www.net.princeton.edu/announcements/ipad-iphoneos32-stops-renewing-lease-keeps-using-IP-address.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/www.net.princeton.edu');">other groups had identified this a long time ago</a>).  My iPhone 4G wouldn&#8217;t get onto the net, and even worse, every time I tried to get onto the net, it would kick my laptop off for a minute or two.</p>
<p>At that point, it became blindingly obvious &#8212; the phone was trying to use an expired lease, and as a result was conflicting with the laptop.  Thirty seconds later I had set up static IPs for the iPad and iPhone 4G, and all my problems were solved.  I could use the devices all over the house, there were no mysterious drops, signal strength was fine, and as a bonus, the mysterious wireless network failures that my laptop was having were solved.</p>
<h2>Lessons Learned</h2>
<p>Well, I really should have done my research &mdash; I could have found the answer to this much earlier.</p>
<p>Why did I think it had something to do with signal strength?  I suspect that the 3.2/4.0 iOS somehow bases the signal strength indicator on DHCP status &mdash; where I was getting one bar before is now three. The alternate explanation is that I tended to use the devices in the more remote places at night, which happened to coincide with the DHCP conflict.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/iphone-4-notes-and-wireless-problem/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Setting Up Incanter and MySQL</title>
		<link>http://www.brool.com/index.php/setting-up-incanter-and-mysql</link>
		<comments>http://www.brool.com/index.php/setting-up-incanter-and-mysql#comments</comments>
		<pubDate>Thu, 21 Jan 2010 19:16:02 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[clojure]]></category>
		<category><![CDATA[coding]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=420</guid>
		<description><![CDATA[Okay, Lein really does make stuff pretty easy.  Rather than wrestling with eleventybillion classpaths, just install Lein.
Create a new project directory with
lein new mydirectory
Change the project.clj file that is autogenerated with:
defproject mydirectory &#8220;1.0.0-SNAPSHOT&#8221; :description &#8220;FIXME: write&#8221;
:dependencies [[org.clojure/clojure "1.1.0-alpha-SNAPSHOT"]
    [org.clojure/clojure-contrib "1.0-SNAPSHOT"]
    [mysql/mysql-connector-java "5.1.6"]
    [incanter/incanter "1.0-master-SNAPSHOT"]])
(that is, [...]]]></description>
			<content:encoded><![CDATA[<p>Okay, Lein really does make stuff pretty easy.  Rather than wrestling with eleventybillion classpaths, just <a href="http://github.com/technomancy/leiningen" onclick="javascript:pageTracker._trackPageview('/outbound/article/github.com');">install Lein</a>.</p>
<p>Create a new project directory with
<div class="codesnip-container" >lein new mydirectory</div>
<p>Change the project.clj file that is autogenerated with:</p>
<div class="codesnip-container" >defproject mydirectory &#8220;1.0.0-SNAPSHOT&#8221; :description &#8220;FIXME: write&#8221;<br />
:dependencies [[org.clojure/clojure "1.1.0-alpha-SNAPSHOT"]<br />
    [org.clojure/clojure-contrib "1.0-SNAPSHOT"]<br />
    [mysql/mysql-connector-java "5.1.6"]<br />
    [incanter/incanter "1.0-master-SNAPSHOT"]])</div>
<p>(that is, add the mysql and incanter dependencies).</p>
<p>Download all the dependencies with
<div class="codesnip-container" >lein deps</div>
<p>Start up a REPL with <i>everything in the classpath</i> by just using
<div class="codesnip-container" >lein repl</div>
<p>Wow, that&#8217;s kind of nice.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/setting-up-incanter-and-mysql/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Tethering an iPhone with SSH and Windows 7</title>
		<link>http://www.brool.com/index.php/tethering-an-iphone-with-ssh-and-windows-7</link>
		<comments>http://www.brool.com/index.php/tethering-an-iphone-with-ssh-and-windows-7#comments</comments>
		<pubDate>Sun, 17 Jan 2010 04:59:10 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[iphone ssh tether jailbreak]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=415</guid>
		<description><![CDATA[I don&#8217;t need to tether through my iPhone &#8212; I always seem to be near a hotspot &#8212; but nonetheless I thought that spending 10 minutes to set it up was worth it, because when you need tethering, you really need tethering.  If you&#8217;re willing to drop $10 bucks there are a couple of [...]]]></description>
			<content:encoded><![CDATA[<p>I don&#8217;t need to tether through my iPhone &mdash; I always seem to be near a hotspot &mdash; but nonetheless I thought that spending 10 minutes to set it up was worth it, because when you need tethering, you <i>really</i> need tethering.  If you&#8217;re willing to drop $10 bucks there are a couple of apps in Cydia that can do this easy (PhoneModem and MyWi, I think), but I just wanted something that I could use in an emergency.</p>
<p>Unfortunately, despite the fact that there were some <a href="http://lifehacker.com/398961/get-your-computer-online-using-your-iphones-data-connection" onclick="javascript:pageTracker._trackPageview('/outbound/article/lifehacker.com');">good guides</a> on how to do it, it turned out there were a few gotchas, and it took significantly longer than 10 minutes.  So, in the hopes that I can save someone else the time:</p>
<p>Use <a href="http://lifehacker.com/398961/get-your-computer-online-using-your-iphones-data-connection" onclick="javascript:pageTracker._trackPageview('/outbound/article/lifehacker.com');">this guide</a>, but:</p>
<ul>
<li>in Windows 7, you&#8217;ll want to use the &#8220;Network and Sharing Center&#8221; (right click on your network icon) to create a new &#8220;computer-to-computer&#8221; network.  This is the one the iPhone will connect to.</li>
<li>When you configure Putty, you&#8217;ll want to make sure you go to the SSH/Tunnels page and a) add a dynamic tunnel to a local port (assume 8080) &mdash; you won&#8217;t need to specify a destination and can leave that blank, and b) go to the &#8220;Connection&#8221; page and specify a keepalive of 5 or so.  This keeps the SSH connection between the computer and the iPhone from dying every 30 seconds.</li>
<li>You <i>cannot</i> use Chrome right now, because it does not properly forward DNS requests to the proxy (it took me hours to figure this out).  Use Firefox and specify a SOCKS v5 proxy at port 8080 (or whatever) for the proxy, but you&#8217;ll also need to make sure to go to the about:config page and change the network.proxy.socks_remote_dns to &#8220;true&#8221;.</li>
<li>Doing things in a particular order makes this work better.  If the 3G connection on the iPhone is not active, then there doesn&#8217;t seem to be a way to activate after it links to your ad hoc connection.  So:  turn off wireless, go to a web page (this activates the 3G), turn on wireless, connect to your computer.  This way both the 3G and wireless connections are established.  An easy way to see if the 3G is active is to run MobileTerminal (or just SSH into the iPhone) and run ipconfig;  if the pdp_ip0 device is pointing to a real IP, then your 3G is active.</li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/tethering-an-iphone-with-ssh-and-windows-7/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Acer 1410 Mini-review</title>
		<link>http://www.brool.com/index.php/acer-1410-mini-review</link>
		<comments>http://www.brool.com/index.php/acer-1410-mini-review#comments</comments>
		<pubDate>Fri, 08 Jan 2010 16:54:48 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[reviews]]></category>
		<category><![CDATA[acer 1410 review]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=408</guid>
		<description><![CDATA[I&#8217;ve had an Asus EEE 1000h ever since they came out, but it was getting to be time to upgrade it &#8212; it was not a bad little machine, but the Atom processor was a bit underpowered, and that damnable right shift key always did bug me.  I picked up an Acer Aspire 1410 [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;ve had an Asus EEE 1000h ever since they came out, but it was getting to be time to upgrade it &#8212; it was not a bad little machine, but the Atom processor was a bit underpowered, and that damnable right shift key always did bug me.  I picked up an Acer Aspire 1410 with Bing cashback for about $370, give or take.</p>
<p>Man, netbooks have really come a long way.  A quick run through:</p>
<p><b>Screen</b>:  1366&#215;768 vs. 1024&#215;600 is almost twice as big, and makes a big difference.  It&#8217;s glossy, which is kind of annoying, and I think the contrast is a little lower than on the 1000h, but nonetheless it&#8217;s really nice.</p>
<p><b>Keyboard</b>:  Full sized shift keys on the Acer!  This far outweighs almost anything else.  The smaller cursor control keys are kind of pain, but I&#8217;ll get used to them.  Feedback is not as nice as the Asus but still pretty decent &#8212; I can type full speed on this keyboard.</p>
<p><b>Touchpad</b>:  Touchpad is good enough;  at least there are two mouse buttons, which is one of the things I really wanted.  It&#8217;s multitouch, but the drivers are a little choppy with the two finger scrolling &#8212; but I haven&#8217;t tried to fix it, either.  The two finger to zoom in and out is surprisingly handy when browsing, to be honest, and I&#8217;m using it all the time.</p>
<p><b>Wireless</b>:  Wireless on my EEE 1000h was always a little glitchy at home (and would sometimes cause my router to reboot, for whatever reason), but was fine at work and at Starbucks.  The wireless on the Acer 1410 works much better, and I haven&#8217;t had any problems. </p>
<p><b>Speaker</b>:  I frequently watch movies with the speakers on.  The speakers seem to be just a touch softer than the EEE 1000h, but still pretty good.  <a href="http://forum.notebookreview.com/showthread.php?t=419117" onclick="javascript:pageTracker._trackPageview('/outbound/article/forum.notebookreview.com');">This tweaks thread has some tips on improving the volume of the speakers.</a></p>
<p><b>Processor</b>:  The new ULV chips are everything that Atom wanted to be.  With the Acer I&#8217;ve been able to a) run Ubuntu under virtualbox, b) play full-screen 480p Hulu, and c) play full-screen Netflix, and it hasn&#8217;t stalled out on anything.  Additionally, the 1000h would bog down when scrolling in Firefox (seriously), whereas this machine handles it fine. </p>
<p>I specifically looked for an Acer with the SU2300 (dual core) instead of the SU3500 (single core, slightly faster).  </p>
<p>The machine only starts up the fan when doing flash video &#8212; fan noise is not too bad and significantly quieter than the EEE 1000h.  The computer itself does not get very warm at all, which is nice.</p>
<p>VirtualBox was a must have, since I wanted to run Ubuntu but didn&#8217;t want to deal with the pain of partitioning and dealing with its peculiarities on a new machine.  I had assumed that having the AMD/Intel virtualization mode was a big win, but it turns out that it <a href="http://tombuntu.com/index.php/2007/10/01/should-you-enable-intels-vt-x-in-virtualbox/" onclick="javascript:pageTracker._trackPageview('/outbound/article/tombuntu.com');">really doesn&#8217;t help performance</a>.  Nonetheless, Virtualbox works fine.  VT-x mode was originally turned forced off, and it was subsequently fixed in the BIOS;  see <a href="http://forum.notebookreview.com/showthread.php?t=419117" onclick="javascript:pageTracker._trackPageview('/outbound/article/forum.notebookreview.com');">this tweaks thread</a> for tips on getting the new BIOS. </p>
<p><b>Battery Life</b>:  Hard to say, but looks like 5-7+ with this machine, whereas I was getting about 4 with the Asus 1000h.</p>
<p><b>Operating System</b>:   I run XP on most of my computers (and didn&#8217;t upgrade any to Vista), but the Acer came with Windows 7 Home Premium.  It&#8217;s pretty and nice and performs well &mdash; I have no complaints.</p>
<p>What a difference a year makes.  These new ULV chips are amazing.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/acer-1410-mini-review/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>A Modest Proposal</title>
		<link>http://www.brool.com/index.php/a-modest-proposal</link>
		<comments>http://www.brool.com/index.php/a-modest-proposal#comments</comments>
		<pubDate>Tue, 01 Sep 2009 16:21:25 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[clojure]]></category>
		<category><![CDATA[coding]]></category>
		<category><![CDATA[clojure compojure php]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=373</guid>
		<description><![CDATA[Warning: a very rambling article; less a solid proposal than me just exploring an idea that may lead to a dead end in a week or two after I&#8217;ve thought about it.
I really enjoy Clojure. Everything seems so well thought out and well designed; in a lot of ways it reminds me of Python, which [...]]]></description>
			<content:encoded><![CDATA[<p><i>Warning: a very rambling article; less a solid proposal than me just exploring an idea that may lead to a dead end in a week or two after I&#8217;ve thought about it.</i></p>
<p>I really enjoy Clojure. Everything seems so well thought out and well designed; in a lot of ways it reminds me of Python, which is three ways to ironic because back in the day I started using Python because it was very Lispy. The cycle of life turns even on computer languages.</p>
<p>But unfortunately, I get the sense that there&#8217;s probably only room for one JVM language to make it big.  As much as I like Clojure, I think that Scala will probably be the one that succeeds.  It&#8217;s got the static typing, it&#8217;s got the Java-like performance, and it&#8217;s got a syntax that&#8217;s close-ish to Java, so it fills the niche that Java fills so well: a programming language that is ideal for large groups of developers.</p>
<p>However, it&#8217;s early enough in the development of Clojure that there&#8217;s the sense that maybe individual efforts could make a difference.  (As a counterexample, Haskell is too far along &mdash; it seems like everything has been done already, or anything that needs to be done requires a deep knowledge of category theory and the latest functional design papers.)</p>
<p>Assuming that I would want to help out Clojure, what could be done?</p>
<p>Donate? Actually, I did that. I figured that I got as many hours of enjoyment out of Clojure as I did out of a typical game, so I contributed the price of a game.</p>
<p>Libraries?  Well, I&#8217;ve written one or two.  Will probably write more.</p>
<p>If Clojure is going to succeed, it needs a <i>niche</i>, an area in which it performs so well that it blows everything else away.  Concurrent programming is one possibility, but there is a lot of competition there.</p>
<p>I have a modest proposal:</p>
<p>Clojure should be more like PHP.</p>
<p>Yes, yes, I know that programming in PHP is socially reprehensible, just one step above people that shop without their shirt while in Walmart and car salesmen.</p>
<p>But what if we were to give Clojure the trappings that make starting developers try it?  Metaphorically, it&#8217;s like <i>Gulliver&#8217;s Travels</i>; it <i>looks</i> like a humorous, light-hearted adventure story, but underneath it&#8217;s biting political satire and deep thoughts.  We lure developers in with the possibility of an easy, light-hearted way to write web sites&#8230; and then once they&#8217;re in there, once they&#8217;ve progressed from manipulating web sites and start to realize the benefits of advanced languages, they can deal with a sane language, built on top of the JVM and with the full power of a Lisp.</p>
<p>So call this Gulliver.</p>
<h2>Why Did PHP Succeed?</h2>
<p>My impression, based on absolutely no citations or hard evidence, is that PHP became popular primarily because it is:</p>
<ul>
<li>Easy to start trying &mdash; start with an HTML page, and just add one statement to start playing around with PHP itself</li>
<li>Easy to access data &mdash; typically, with MySQL</li>
<li>Easy to deploy &mdash; just upload a file and go</li>
</ul>
<p>So, continuing the gedankenexperiment: if we were designing something that would be very approachable and very easy to use, what would it look like?</p>
<h2>Making Compojure More Approachable</h2>
<p>Compojure is an excellent base to start with, but it strays away from templates, and instead tries to do everything with compojure.html, a library that allows you to form everything with vectors and lists:</p>
<div class="codesnip-container" >
<div class="lisp codesnip" style="font-family:monospace;"><span class="br0">&#40;</span>html <span class="br0">&#91;</span><span class="sy0">:</span><span class="me1">p</span> <span class="st0">&quot;2 + 2 = &quot;</span> <span class="br0">&#40;</span>+ <span class="nu0">2</span> <span class="nu0">2</span><span class="br0">&#41;</span><span class="br0">&#93;</span><span class="br0">&#41;</span></div>
</div>
<p>Handy? Yes, if you&#8217;re a developer. But if a web designer is doing your HTML, or if you&#8217;re just starting out programming and you already know HTML, though, it seems an additional barrier to entry.  So what if we turn it inside out and do it like PHP does it?</p>
<div class="codesnip-container" >
<div class="html4strict codesnip" style="font-family:monospace;"><span class="sc2">&lt;<a href="http://december.com/html/4/element/p.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/december.com');"><span class="kw2">p</span></a>&gt;</span>2 + 2 = <span class="sc2">&lt;?<span class="sy0">=</span> <span class="br0">&#40;</span>+ <span class="nu0">2</span> <span class="nu0">2</span><span class="br0">&#41;</span> ?&gt;</span></div>
</div>
<p>Trying something more complicated, in compojure.html this:</p>
<div class="codesnip-container" >
<div class="lisp codesnip" style="font-family:monospace;"><span class="br0">&#40;</span>html <span class="br0">&#91;</span><span class="sy0">:</span><span class="me1">ul</span> <span class="br0">&#40;</span>map <span class="br0">&#40;</span>fn <span class="br0">&#91;</span>x<span class="br0">&#93;</span> <span class="br0">&#91;</span><span class="sy0">:</span><span class="me1">li</span> x<span class="br0">&#93;</span><span class="br0">&#41;</span> <span class="br0">&#40;</span>range <span class="nu0">10</span><span class="br0">&#41;</span><span class="br0">&#41;</span><span class="br0">&#93;</span><span class="br0">&#41;</span></div>
</div>
<p>becomes:</p>
<div class="codesnip-container" >
<div class="html4strict codesnip" style="font-family:monospace;"><span class="sc2">&lt;<a href="http://december.com/html/4/element/ul.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/december.com');"><span class="kw2">ul</span></a>&gt;</span><br />
&nbsp; <span class="sc2">&lt;? <span class="br0">&#40;</span>dotimes <span class="br0">&#91;</span>x <span class="nu0">10</span><span class="br0">&#93;</span> ?&gt;</span><br />
&nbsp; <span class="sc2">&lt;<a href="http://december.com/html/4/element/li.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/december.com');"><span class="kw2">li</span></a>&gt;&lt;?<span class="sy0">=</span> x ?&gt;</span><br />
&nbsp; <span class="sc2">&lt;? <span class="br0">&#41;</span> ?&gt;</span><br />
<span class="sc2">&lt;<span class="sy0">/</span><a href="http://december.com/html/4/element/ul.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/december.com');"><span class="kw2">ul</span></a>&gt;</span></div>
</div>
<p>A little bit longer, but treating it as HTML makes it conceptually easier for beginning programmers to understand, especially if you want to do something like changing the id or class with every row so your CSS can make it all pretty:</p>
<div class="codesnip-container" >
<div class="html4strict codesnip" style="font-family:monospace;"><span class="sc2">&lt;<a href="http://december.com/html/4/element/ul.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/december.com');"><span class="kw2">ul</span></a>&gt;</span><br />
&nbsp; <span class="sc2">&lt;? <span class="br0">&#40;</span>dotimes <span class="br0">&#91;</span>x <span class="nu0">10</span><span class="br0">&#93;</span> ?&gt;</span><br />
&nbsp; <span class="sc2">&lt;<a href="http://december.com/html/4/element/li.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/december.com');"><span class="kw2">li</span></a> <span class="kw3">id</span><span class="sy0">=</span><span class="st0">&quot;list-&lt;?= x ?&gt;</span></span>&quot; class=&quot;<span class="sc2">&lt;?<span class="sy0">=</span> <span class="br0">&#40;</span>if <span class="br0">&#40;</span>even? x<span class="br0">&#41;</span> <span class="st0">&quot;even&quot;</span> <span class="st0">&quot;odd&quot;</span><span class="br0">&#41;</span> ?&gt;</span>&quot;&gt;<span class="sc2">&lt;?<span class="sy0">=</span> x ?&gt;&lt;<span class="sy0">/</span><a href="http://december.com/html/4/element/li.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/december.com');"><span class="kw2">li</span></a>&gt;</span><br />
&nbsp; <span class="sc2">&lt;? <span class="br0">&#41;</span> ?&gt;</span><br />
<span class="sc2">&lt;<span class="sy0">/</span><a href="http://december.com/html/4/element/ul.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/december.com');"><span class="kw2">ul</span></a>&gt;</span></div>
</div>
<p>Doing this is compojure.html is trickier:</p>
<div class="codesnip-container" >
<div class="lisp codesnip" style="font-family:monospace;"><span class="br0">&#40;</span>html <br />
&nbsp; <span class="br0">&#91;</span><span class="sy0">:</span><span class="me1">ul</span> <br />
&nbsp; &nbsp; <span class="br0">&#40;</span>map <span class="br0">&#40;</span>fn <span class="br0">&#91;</span>x<span class="br0">&#93;</span> <span class="br0">&#91;</span><span class="sy0">:</span><span class="me1">li</span> <span class="br0">&#123;</span><span class="sy0">:</span><span class="me1">id</span> <span class="br0">&#40;</span>str <span class="st0">&quot;list-&quot;</span> x<span class="br0">&#41;</span> <span class="sy0">:</span><span class="me1">class</span> <span class="br0">&#40;</span><span class="kw1">if</span> <span class="br0">&#40;</span>even? x<span class="br0">&#41;</span> <span class="st0">&quot;even&quot;</span> <span class="st0">&quot;odd&quot;</span><span class="br0">&#41;</span><span class="br0">&#125;</span> x<span class="br0">&#93;</span><span class="br0">&#41;</span> <br />
&nbsp; &nbsp; <span class="br0">&#40;</span>range <span class="nu0">10</span><span class="br0">&#41;</span><span class="br0">&#41;</span><span class="br0">&#93;</span><span class="br0">&#41;</span></div>
</div>
<p>So, let&#8217;s lure people in with easy to use, and they can pick up vectors and S-exprs and notational convenience later.  Converting a template file into the basic code is easy:</p>
<div class="codesnip-container" >
<div class="lisp codesnip" style="font-family:monospace;"><span class="br0">&#40;</span>defn- transform-string<br />
&nbsp; <span class="st0">&quot;Internal. &nbsp;Transform a string into the appropriate echo statement.<br />
An empty string translates into a single space.&quot;</span> &nbsp;<br />
&nbsp; <span class="br0">&#91;</span>s<span class="br0">&#93;</span><br />
&nbsp; <span class="br0">&#40;</span><span class="kw1">if</span> <span class="br0">&#40;</span><span class="sy0">&gt;</span> <span class="br0">&#40;</span><span class="sy0">.</span><span class="kw1">length</span> s<span class="br0">&#41;</span> <span class="nu0">0</span><span class="br0">&#41;</span><br />
&nbsp; &nbsp; <span class="br0">&#40;</span>format <span class="st0">&quot;(gulliver/echo %s)&quot;</span> <span class="br0">&#40;</span>pr-str s<span class="br0">&#41;</span><span class="br0">&#41;</span><br />
&nbsp; <span class="st0">&quot; &quot;</span><span class="br0">&#41;</span><span class="br0">&#41;</span></p>
<p><span class="br0">&#40;</span>defn- transform-code<br />
&nbsp; <span class="st0">&quot;Internal. &nbsp;Transform code so that it can run as a render routine.&quot;</span><br />
&nbsp; <span class="br0">&#91;</span>s<span class="br0">&#93;</span><br />
&nbsp; <span class="br0">&#40;</span><span class="kw1">if</span> <span class="br0">&#40;</span><span class="sy0">=</span> <span class="br0">&#40;</span>first s<span class="br0">&#41;</span> \<span class="sy0">=</span><span class="br0">&#41;</span><br />
&nbsp; &nbsp; <span class="br0">&#40;</span>format <span class="st0">&quot;(gulliver/echo %s)&quot;</span> <span class="br0">&#40;</span><span class="sy0">.</span>substring s <span class="nu0">1</span><span class="br0">&#41;</span><span class="br0">&#41;</span><br />
&nbsp; &nbsp; s<span class="br0">&#41;</span><span class="br0">&#41;</span></p>
<p><span class="br0">&#40;</span>defn- convert* <br />
&nbsp; <span class="st0">&quot;Internal. &nbsp;Given a string that represents a Clojure template,<br />
produce a flat list of the statements necessary to produce that template.&quot;</span><br />
&nbsp; <span class="br0">&#91;</span>s<span class="br0">&#93;</span><br />
&nbsp; <span class="br0">&#40;</span><span class="kw1">let</span> <span class="br0">&#91;</span>m <span class="br0">&#40;</span>re-matcher #<span class="st0">&quot;(?s)(.*?)&lt;<span class="es0">\?</span>(.+?)<span class="es0">\?</span>&gt;|(.+?)$&quot;</span> s<span class="br0">&#41;</span><span class="br0">&#93;</span><br />
&nbsp; &nbsp; <span class="br0">&#40;</span>loop <span class="br0">&#91;</span>next <span class="br0">&#40;</span>re-find m<span class="br0">&#41;</span> buffer <span class="br0">&#91;</span><span class="st0">&quot;&#8217;(&quot;</span><span class="br0">&#93;</span><span class="br0">&#93;</span><br />
&nbsp; &nbsp; &nbsp; <span class="br0">&#40;</span><span class="kw1">cond</span><br />
&nbsp; &nbsp; &nbsp; &nbsp;<span class="br0">&#40;</span><span class="kw1">not</span> <span class="br0">&#40;</span><span class="kw1">nil</span>? <span class="br0">&#40;</span><span class="kw1">nth</span> next 3<span class="br0">&#41;</span><span class="br0">&#41;</span><span class="br0">&#41;</span> <br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span class="br0">&#40;</span><span class="kw1">eval</span> <span class="br0">&#40;</span>read-string <span class="br0">&#40;</span><span class="kw1">apply</span> str <span class="br0">&#40;</span>conj buffer <span class="br0">&#40;</span>transform-string <span class="br0">&#40;</span><span class="kw1">nth</span> next <span class="nu0">3</span><span class="br0">&#41;</span><span class="br0">&#41;</span> <span class="st0">&quot;)&quot;</span> <span class="br0">&#41;</span><span class="br0">&#41;</span><span class="br0">&#41;</span><span class="br0">&#41;</span><br />
&nbsp; &nbsp; &nbsp; &nbsp;<span class="sy0">:</span><span class="me1">otherwise</span> <span class="br0">&#40;</span>recur <br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span class="br0">&#40;</span>re-find m<span class="br0">&#41;</span> <br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span class="br0">&#40;</span>conj buffer <br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span class="br0">&#40;</span>transform-string <span class="br0">&#40;</span><span class="kw1">nth</span> next 1<span class="br0">&#41;</span><span class="br0">&#41;</span> <br />
&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp;<span class="br0">&#40;</span>transform-code <span class="br0">&#40;</span><span class="kw1">nth</span> next <span class="nu0">2</span><span class="br0">&#41;</span><span class="br0">&#41;</span><span class="br0">&#41;</span><span class="br0">&#41;</span><br />
<span class="br0">&#41;</span><span class="br0">&#41;</span><span class="br0">&#41;</span><span class="br0">&#41;</span></div>
</div>
<p>Resulting in&#8230;</p>
<div class="codesnip-container" >
<div class="lisp codesnip" style="font-family:monospace;"><span class="sy0">==&gt;</span> <span class="br0">&#40;</span>convert* <span class="st0">&quot;&lt;ul&gt;&lt;? (dotimes [x 10] ?&gt;&lt;li&gt;&lt;?= x ?&gt;&lt;/li&gt;&lt;? ) ?&gt;&lt;/ul&gt;&quot;</span><span class="br0">&#41;</span></p>
<p><span class="br0">&#40;</span><span class="br0">&#40;</span>gulliver/echo <span class="st0">&quot;&lt;ul&gt;&quot;</span><span class="br0">&#41;</span> <span class="br0">&#40;</span><span class="kw1">dotimes</span> <span class="br0">&#91;</span>x <span class="nu0">10</span><span class="br0">&#93;</span> <span class="br0">&#40;</span>gulliver/echo <span class="st0">&quot;&lt;li&gt;&quot;</span><span class="br0">&#41;</span> <span class="br0">&#40;</span>gulliver/echo x<span class="br0">&#41;</span> <span class="br0">&#40;</span>gulliver/echo <span class="st0">&quot;&lt;/li&gt;&quot;</span><span class="br0">&#41;</span><span class="br0">&#41;</span> <span class="br0">&#40;</span>gulliver/echo <span class="st0">&quot;&lt;/ul&gt;&quot;</span><span class="br0">&#41;</span><span class="br0">&#41;</span></div>
</div>
<p>Once you have the basic code generation, it&#8217;s easy enough to hook it up to a default servlet that automatically invokes it when necessary. There&#8217;s a fair bit of handwaving going on here &mdash; regexes are questionable for this, there are some interesting issues with namespaces, and it would require some method of resolving dependencies between files, but heck, it&#8217;s only 100 lines of code;  it was really quick to put together and gives us a sense of whether this can work out.</p>
<p>So, with the <a href="http://github.com/brool/gulliver/tree/master" onclick="javascript:pageTracker._trackPageview('/outbound/article/github.com');">source on github</a>, your basic server becomes&#8230;</p>
<pre class="brush: php">
(use &#039;gulliver)
(defserver web-server
  {:port 8080}
  &quot;/*&quot;  (servlet gulliver/template-servlet))
</pre>
<p>Easy!  As an test, an example file:</p>
<pre class="brush: php">
&lt;?
(import &#039;java.util.Date)
?&gt;

&lt;html&gt;
  &lt;body&gt;
    &lt;h1&gt;Delivered via Gulliver&lt;/h1&gt;
    &lt;p&gt;Expressions at work: &lt;?= (+ 2 2) ?&gt;&lt;/p&gt;
    &lt;p&gt;Looping:&lt;/p&gt;
    &lt;ul&gt;
    &lt;? (dotimes [x 10] ?&gt;
      &lt;li&gt;&lt;?= x ?&gt;&lt;/li&gt;
    &lt;? ) ?&gt;
    &lt;/ul&gt;

    &lt;p&gt;Here&#039;s a date:  &lt;?= (Date.) ?&gt;&lt;/p&gt;
  &lt;/body&gt;
&lt;/html&gt;
</pre>
<p>&#8230; does the right thing. How about a time test?</p>
<pre class="brush: php">
&lt;html&gt;
    &lt;body&gt;
    &lt;h1&gt;Starting time test...&lt;/h1&gt;
    &lt;? (let [ start (System/currentTimeMillis) ] ?&gt;
    &lt;p&gt;Adding 1..100000:  &lt;?= (reduce + 0 (range 1 1000001)) ?&gt;&lt;/p&gt;
    &lt;p&gt;(took &lt;?= (- (System/currentTimeMillis) start) ?&gt; ms)&lt;/p&gt;
    &lt;? ) ?&gt;
    &lt;/body&gt;
&lt;/html&gt;
</pre>
<p>&#8230; runs in about 50ms.  PHP takes about 130ms on the same sequence on my laptop, so, while there are tons of optimizations we could do (like not doing a stat on the file every time the page is rendered (!)), it nonetheless performs well enough that maybe this is a viable option. Finally, as a special bonus, a stupid eval trick that evaluates Clojure code:</p>
<pre class="brush: php">
&lt;html&gt;
    &lt;body&gt;
        &lt;? (when ((request :params) :code) ?&gt;
        &lt;pre style=&quot;border: 1px dotted&quot;&gt;
        &lt;?= (str (eval (read-string ((request :params) :code)))) ?&gt;
        &lt;/pre&gt;
        &lt;? ) ?&gt;
        &lt;form method=&quot;post&quot;&gt;
        &lt;textarea name=&quot;code&quot; rows=10 cols=80&gt;&lt;/textarea&gt;&lt;br/&gt;
        &lt;input type=&quot;submit&quot; value=&quot;Evaluate&quot; /&gt;
        &lt;/form&gt;
    &lt;/body&gt;
&lt;/html&gt;
</pre>
<p>Take that, non-dynamic languages!</p>
<p><a href="http://github.com/brool/gulliver/tree/master" onclick="javascript:pageTracker._trackPageview('/outbound/article/github.com');">Github copy of the source</a></p>
<p>.</p>
<p>Next part:  Schema-ing Against MySQL</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/a-modest-proposal/feed</wfw:commentRss>
		<slash:comments>9</slash:comments>
		</item>
		<item>
		<title>Snippet: Automatic Proxy Creation in Clojure</title>
		<link>http://www.brool.com/index.php/snippet-automatic-proxy-creation-in-clojure</link>
		<comments>http://www.brool.com/index.php/snippet-automatic-proxy-creation-in-clojure#comments</comments>
		<pubDate>Fri, 21 Aug 2009 22:20:42 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[clojure]]></category>
		<category><![CDATA[coding]]></category>
		<category><![CDATA[macro]]></category>
		<category><![CDATA[proxy]]></category>
		<category><![CDATA[snippet]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=366</guid>
		<description><![CDATA[The proxy function makes it easy for Clojure to interface with the Java layer, but I was dealing with an interface (the AIM Java API) that had an punitive number of things that needed to be overridden&#8230;

public void OnIdleStateChange(AccSession arg0, int arg1) {
}

public void OnInstanceChange(AccSession arg0, AccInstance arg1, AccInstance arg2, AccInstanceProp arg3) {
}

public void OnLookupUsersResult(AccSession [...]]]></description>
			<content:encoded><![CDATA[<p>The proxy function makes it easy for Clojure to interface with the Java layer, but I was dealing with an interface (the AIM Java API) that had an punitive number of things that needed to be overridden&#8230;</p>
<pre class="brush: java">
public void OnIdleStateChange(AccSession arg0, int arg1) {
}

public void OnInstanceChange(AccSession arg0, AccInstance arg1, AccInstance arg2, AccInstanceProp arg3) {
}

public void OnLookupUsersResult(AccSession arg0, String[] arg1, int arg2, AccResult arg3, AccUser[] arg4) {
}

public void OnSearchDirectoryResult(AccSession arg0, int arg1, AccResult arg2, AccDirEntry arg3) {
}

// ... go on like this for pages
</pre>
<p>The Java code is <a href="http://dev.aol.com/aimclient/OpenAIM182/samples/accjsample/AccJSample.java" onclick="javascript:pageTracker._trackPageview('/outbound/article/dev.aol.com');">here</a>, if you&#8217;re interested in the entire set of calls.  Now, I didn&#8217;t care about most of those events, but I had to override them, since they didn&#8217;t have a default implementation.  What made this seem painful was that I was really only interested in two of the callbacks.  So I started to record an Emacs macro to convert the Java code to the equivalent Clojure proxy statement, and then I realized that I didn&#8217;t have to &mdash; <i>I was using a Lisp</i>.</p>
<pre class="brush: php">
(defmacro auto-proxy [interfaces variables &amp; args]
  (let [defined (set (map #(str (first %)) args))
        names (fn [i] (map #(.getName %) (.getMethods i)))
        all-names (into #{} (apply concat (map names (map resolve interfaces))))
        undefined (difference all-names defined)
        auto-gen (map (fn [x] `(~(symbol x) [&amp; ~&#039;args])) undefined)]
    `(proxy ~interfaces ~variables ~@args ~@auto-gen)))
</pre>
<p>Auto-proxy works just like proxy, but it makes an empty implementation for any call that wasn&#8217;t defined.  So, suddenly, what would have been a bunch of lines collapsed into just:</p>
<pre class="brush: php">
(defn create-aim-proxy []
  (auto-proxy [com.aol.acc.AccEvents] []
     (OnImReceived [session imSession participant im]
        (handle-im session imSession participant im))
     (OnStateChange [arg0 arg1 arg2]
        (handle-state-change arg0 arg1 arg2))))
</pre>
<p>Macros ftw.  The nice thing about Clojure/Lisp is that it makes coding up this kind of reusable framework stuff really easy.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/snippet-automatic-proxy-creation-in-clojure/feed</wfw:commentRss>
		<slash:comments>7</slash:comments>
		</item>
		<item>
		<title>Pattern Matching In Clojure</title>
		<link>http://www.brool.com/index.php/pattern-matching-in-clojure</link>
		<comments>http://www.brool.com/index.php/pattern-matching-in-clojure#comments</comments>
		<pubDate>Wed, 12 Aug 2009 09:38:57 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[clojure]]></category>
		<category><![CDATA[coding]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[matching]]></category>
		<category><![CDATA[ocaml]]></category>
		<category><![CDATA[pattern]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=351</guid>
		<description><![CDATA[Updated:  Note that this is available as a clojars module.
Clojure code density seems to be pretty good. There are a fair number of convenient shortforms in the language; for example, associative datatypes all act as a function &#8212; so given a hash map you can reference it with (my-hashmap :key).  The base language [...]]]></description>
			<content:encoded><![CDATA[<p><b>Updated</b>:  Note that this is available as a <a href="http://clojars.org/pattern-match" onclick="javascript:pageTracker._trackPageview('/outbound/article/clojars.org');">clojars module</a>.</p>
<p>Clojure code density seems to be pretty good. There are a fair number of convenient shortforms in the language; for example, associative datatypes all act as a function &mdash; so given a hash map you can reference it with (my-hashmap :key).  The base language itself is probably about as expressive as Python (or a bit better), but you have the added advantage of being able to use macros as needed to really get the code density up.</p>
<p>Nonetheless, I really wanted something like Ocaml&#8217;s / Haskell&#8217;s pattern matching; it makes some code wonderfully concise.</p>
<p>Accordingly, I hacked something up, based on Clojure&#8217;s built-in destructuring. Some examples:</p>
<p>Literal values match against the same value, while _ matches against any non-nil value (and nil matches against any nil one).  Additionally, :when clauses can be used for conditional checks.</p>
<pre class="brush: php">
; simple recursive evaluator
(defn arithmetic [lst]
  (match lst
    v  :when (number? v)  v
    [ _ &quot;error&quot; _]     &quot;error&quot;
    [ _ _ &quot;error&quot;]     &quot;error&quot;
    [ &quot;add&quot; a b ]      (+ (arithmetic a) (arithmetic b))
    [ &quot;sub&quot; a b ]      (- (arithmetic a) (arithmetic b))
    [ &quot;mul&quot; a b ]      (* (arithmetic a) (arithmetic b))
    [ &quot;div&quot; a b ]      (/ (arithmetic a) (arithmetic b))
    [ &quot;squared&quot; a ]    (arithmetic [&quot;mul&quot; (arithmetic a) (arithmetic a)])
    _                  &quot;error&quot; ))
</pre>
<p>Both collections and single values can be used:</p>
<pre class="brush: php">
;; return signum fr a number
(defn signum [x]
  (match x
     0 0
     n :when (&lt; n 0) -1
     _ 1))
</pre>
<p>The pattern matching is stricter than the typical destructure;  whereas [ a b ] will destructure against a list of any number of elements, [ a b ] will pattern match only against a list of two elements.</p>
<pre class="brush: php">
(match x
    []    &quot;empty&quot;
    [_]   &quot;one element&quot;
    [a a] &quot;two identical elements&quot;
    [_ _] &quot;two elements&quot;
    _     &quot;three or more&quot;)
</pre>
<p>If the same variable occurs in multiple locations in the parameter list, it will be checked for equality.  The &#038; tail form can be used to specify the rest of the list.</p>
<pre class="brush: php">
;; count identical elements in the same location in two lists:
(defn count= [ lst1 lst2 ]
  (loop [ a lst1 b lst2 count 0 ]
    (match [a b]
      [[e &amp; at] [e &amp; bt]]  (recur at bt (inc count))
      [[_ &amp; at] [_ &amp; bt]]  (recur at bt count)
      _                    count)))
</pre>
<p>Note that this is slightly more flexible than Haskell / ML, in that a variable of the same name can be multiple places in the pattern.</p>
<h3>Defining</h3>
<p>You can use the defnp macro to define a function that is pattern matched; it defines a function that takes one argument and has an implicit match statement.  For example, the signum function can be written:</p>
<pre class="brush: php">
    (defnp signum
       0 0
       n :when (&lt; n 0) -1
       _ 1)
</pre>
<p>(Thanks to <a href="http://infolace.blogspot.com/" onclick="javascript:pageTracker._trackPageview('/outbound/article/infolace.blogspot.com');">Tom Faulhaber</a> for suggesting this)</p>
<h3>Gotchas</h3>
<p>The Clojure destructuring will cause an exception if you try to destructure a collection type with a value.</p>
<pre class="brush: php">
(let [[a b] 10] a)
java.lang.UnsupportedOperationException: nth not supported on this type: Integer (NO_SOURCE_FILE:0)
</pre>
<p>&#8230; so be sure to check such cases early in your match statement, if they are possible.</p>
<h3>How It Works</h3>
<p>The pattern matcher uses the built-in Clojure destructuring as the main mechanism, but adorns it so that the pattern can be verified.  For example, the code:</p>
<pre class="brush: php">
(match x [a a] &quot;two identical&quot; )
</pre>
<p>turns into essentially the following:</p>
<pre class="brush: php">
(let [ [ a g0001 &amp; g0002 ] x ]
     (if (and (not (nil? a)) (= g0001 a) (nil? g0002)) &quot;two identical&quot; nil))
</pre>
<p>That is, the destructuring is done, but then the two variables are checked to make sure that they are equal, and the list is checked to make sure it is only two elements long.</p>
<h3>Source</h3>
<p><a href="http://github.com/brool/clojure-misc/tree" onclick="javascript:pageTracker._trackPageview('/outbound/article/github.com');">It&#8217;s all on Github</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/pattern-matching-in-clojure/feed</wfw:commentRss>
		<slash:comments>10</slash:comments>
		</item>
		<item>
		<title>aset is Faster Than aset-int</title>
		<link>http://www.brool.com/index.php/aset-is-faster-than-aset-int</link>
		<comments>http://www.brool.com/index.php/aset-is-faster-than-aset-int#comments</comments>
		<pubDate>Sat, 08 Aug 2009 21:51:13 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[clojure]]></category>
		<category><![CDATA[coding]]></category>
		<category><![CDATA[array]]></category>
		<category><![CDATA[performance]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=345</guid>
		<description><![CDATA[Clojure isn&#8217;t the fastest functional lanuage &#8212; that title seems to go to Haskell these days, at least for the stuff that I do &#8212; but it nonetheless is usually fast enough.  It&#8217;s a dynamic language, so is perhaps cursed to be somewhat slower always, but nonetheless for the things that I do, it [...]]]></description>
			<content:encoded><![CDATA[<p>Clojure isn&#8217;t the fastest functional lanuage &#8212; that title seems to go to Haskell these days, at least for the stuff that I do &#8212; but it nonetheless is usually fast enough.  It&#8217;s a dynamic language, so is perhaps cursed to be somewhat slower always, but nonetheless for the things that I do, it seems to be about 2-4x slower than Ocaml/Haskell and substantially faster than Python.</p>
<p>Nonetheless, I ran into a situation where it seemed to be 100x slower than Java because of an erroneous assumption on my part. After stripping out and profiling and removing everything extraneous, it finally came down to array access. Ignoring the uselessness of this snippet for a while, the issue is how to translate something like the following code:</p>
<pre class="brush: java">
int v[] = new int[1000];
java.util.Arrays.fill(v, 0);
for (int i = 0; i &lt; 100000; i++)
    for (int ix = 0; ix &lt; 1000; ix++) {
        v[ix]++;
        v[ix]--;
}
</pre>
<p>&#8230; which runs in about 350ms on my Macbook.  My pass at the Clojure equivalent, with the type hinting:</p>
<pre class="brush: php">
;; this is 100x slower than the equivalent in Java
(defn useless-array-manipulation []
  (let [v (int-array 1000)]
    (java.util.Arrays/fill v 0)
    (dotimes [_ (int 100000)]
      (dotimes [ix (int 1000)]
        (aset-int v ix (unchecked-add (int 1) (aget v ix)))
        (aset-int v ix (unchecked-subtract (int 1) (aget v ix)))))))
</pre>
<p>&#8230; which takes about 40692ms &#8212; more than 100x slower.  What the hell?  After many hours of Googling, I finally discovered from <a href="http://www.fatvat.co.uk/2009/01/ray-tracing-in-clojure-part-ii.html" onclick="javascript:pageTracker._trackPageview('/outbound/article/www.fatvat.co.uk');">the comments on this blog post</a> that aset-int is slower than aset, which I don&#8217;t recall seeing anywhere else. Does it really make a difference?</p>
<pre class="brush: php">
;; much faster
(defn useless-array-manipulation []
  (let [v (int-array 1000)]
    (java.util.Arrays/fill v 0)
    (dotimes [_ (int 100000)]
      (dotimes [ix (int 1000)]&gt;
        (aset v ix (unchecked-add (aget v ix) (int 1)))
        (aset v ix (unchecked-subtract (aget v ix) (int 1)))))))
</pre>
<p>&#8230; runs in about 1000ms, or about 3x slower than the Java variant, and is definitely something that I can live with. I had been assuming that aset-int was of course faster because it was more specific, but in fact (aset v ix (int val)) is <i>much faster</i> than (aset-int v ix val).</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/aset-is-faster-than-aset-int/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Tokyo Cabinet API for Clojure</title>
		<link>http://www.brool.com/index.php/tokyo-cabinet-api-for-clojure</link>
		<comments>http://www.brool.com/index.php/tokyo-cabinet-api-for-clojure#comments</comments>
		<pubDate>Fri, 07 Aug 2009 01:51:56 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[clojure]]></category>
		<category><![CDATA[coding]]></category>
		<category><![CDATA[kvstore]]></category>
		<category><![CDATA[nonsql]]></category>
		<category><![CDATA[tokyo cabinet]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=333</guid>
		<description><![CDATA[I&#8217;ve been playing with Tokyo Cabinet and Clojure for a bit, and while I will go on about both of them in another blog post (or not), I have to mention that Clojure is such a well designed language that it&#8217;s a pleasure to play with.  It has much of the same intrinsic power [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;ve been playing with Tokyo Cabinet and Clojure for a bit, and while I will go on about both of them in another blog post (or not), I have to mention that Clojure is such a well designed language that it&#8217;s a pleasure to play with.  It has much of the same intrinsic power as Haskell, but in a fashion that might be more approachable for people coming from Python or Ruby.</p>
<p>At any rate, I made a small, thin layer around the Tokyo Cabinet API, and <a href="http://github.com/brool/tokyo-cabinet/tree/master" onclick="javascript:pageTracker._trackPageview('/outbound/article/github.com');">put it on Github</a>.  Another thin wrapper can be found <a href="http://justin.harmonize.fm/index.php/tag/tokyo-cabinet/" onclick="javascript:pageTracker._trackPageview('/outbound/article/justin.harmonize.fm');">at this blog</a>.</p>
<p>Copy of the README is below (the ultimate in lazy!).</p>
<h3>Introduction</h3>
<p>This is a simple interface to the Tokyo Cabinet libraries.  Tokyo Cabinet is a very cool, very high performing key-value store.  This library supports table mode, which essentially means that arbitrary hashmaps can be stored in the cabinet.</p>
<p>Note that this is appropriate for local storage only &#8212; if you&#8217;re looking to share a Tokyo Cabinet to multiple computers, you actually want Tokyo Tyrant.</p>
<h3>Basic Usage</h3>
<p>The with-cabinet call creates/opens a cabinet and allows the use of the various access routines within the scope of the call.  For example, here&#8217;s how to create a cabinet with three entries.</p>
<pre class="brush: php">
(ns user (:use tokyo-cabinet))  ;; bring into our namespace

(with-cabinet { :filename &quot;test.tokyo&quot; :mode (+ OWRITER OCREAT) }
    (doseq [[name val] [[&quot;1&quot; &quot;one&quot;] [&quot;2&quot; &quot;two&quot;] [&quot;3&quot; &quot;three&quot;]]]
        (put-value name val)))
</pre>
<p>This creates a Tokyo Cabinet <i>hash table</i>, which allows one value per key.  Now query an entry:</p>
<pre class="brush: php">
(with-cabinet { :filename &quot;test.tokyo&quot; :mode OREADER }
    (get-value &quot;1&quot;))
&quot;one&quot;
</pre>
<h3>Tables</h3>
<p>A <i>table</i> in Tokyo Cabinet can be used to store arbitrary hash maps.  For example:</p>
<pre class="brush: php">
(def params { :filename &quot;test-table.tokyo&quot; :mode (+ OWRITER OCREAT) :type :table } )
(with-cabinet params
    (put-value nil { :name &quot;John Doe&quot; :hobbies &quot;rowing fishing skiing&quot; :age 28 :gender &quot;M&quot; })
    (put-value nil { :name &quot;Melissa Swift&quot; :hobbies &quot;soccer tennis books&quot; :age 33 :gender &quot;F&quot;})
    (put-value nil { :name &quot;Tom Swift&quot; :hobbies &quot;inventing exploring&quot; :gender &quot;M&quot; })
    (put-value nil { :name &quot;Harry Potter&quot; :hobbies &quot;magic quidditch flying&quot; :gender &quot;M&quot; :age 9 }))
</pre>
<h3>Queries</h3>
<p>Queries can be run, and you can use (hint) to take a look at how the query is being performed:</p>
<pre class="brush: php">
; show a hint and all rows matching
(defn showrows [query]
    (let [showhint (atom false)]
        (with-query-results row query
            (when (compare-and-set! showhint false true)
                  (println &quot;Query: &quot; query)
                  (println &quot;Hint: &quot; (hint))
                  (println &quot;Results:&quot;))
            (println row)))
        (println))

(with-cabinet params
    (showrows [[:age &quot;&gt;=&quot; 30]])
    (showrows [[:hobbies &quot;any-token&quot; &quot;soccer&quot;]]))
</pre>
<p>Leads to the following output:</p>
<pre class="brush: php">
Query:  [[:age &gt;= 30]]
Hint:  scanning the whole table
result set size: 1
leaving the natural order

Results:
{:gender F, :hobbies soccer tennis books, :name Melissa Swift, :age 33}

Query:  [[:hobbies any-token soccer]]
Hint:  scanning the whole table
result set size: 1
leaving the natural order

Results:
{:gender F, :hobbies soccer tennis books, :name Melissa Swift, :age 33}
</pre>
<h3>Indexes</h3>
<p>Indexes can be added with create-index (and removed with delete-index), which help optimize particular queries.</p>
<p>The different index types:</p>
<ul>
<li>INDEX-DECIMAL</li>
<li>INDEX-LEXICAL</li>
<li>INDEX-QGRAM</li>
</ul>
<p>With some optional specifiers that can be added / ored in:</p>
<ul>
<li>INDEX-KEEP &#8212; keep the index if it already exists</li>
<li>INDEX-OPTIMIZE</li>
</ul>
<p>Running the queries again, with indexes:</p>
<pre class="brush: php">
; indexes are persistent
(with-cabinet params
    (create-index :hobbies INDEX-TOKEN)
    (create-index :age INDEX-DECIMAL))

; try the queries again with the indexes in place
(with-cabinet params
    (showrows [[:age &quot;&gt;=&quot; 30]])
    (showrows [[:hobbies &quot;any-token&quot; &quot;soccer&quot;]]))
</pre>
<p>Gets the following hint:</p>
<pre class="brush: php">
Query:  [[:age &gt;= 30]]
Hint:  using an index: &quot;:age&quot; asc (NUMGT/NUMGE)
result set size: 1
leaving the natural order

Results:
{:gender F, :hobbies soccer tennis books, :name Melissa Swift, :age 33}

Query:  [[:hobbies any-token soccer]]
Hint:  using an index: &quot;:hobbies&quot; inverted (STROR)
token occurrence: &quot;soccer&quot; 1
result set size: 1
leaving the natural order

Results:
{:gender F, :hobbies soccer tennis books, :name Melissa Swift, :age 33}
</pre>
<h3>Optional Search Parameters</h3>
<p>You can further control what&#8217;s fetched by using a number of optional specifiers in the query:</p>
<ul>
<li>:limit nnn &#8212; limits the number of rows returned</li>
<li>:skip  nnn &#8212; skips the first nnn rows</li>
<li>:sort  fieldname &#8212; sorts by the given field</li>
<li>:order val &#8212; the specific ordering, one of SORT-NUM-ASC, SORT-NUM-DESC, SORT-TEXT-ASC, or SORT-TEXT-DESC</li>
</ul>
<p>For example:</p>
<pre class="brush: php">
(with-cabinet params (with-query-results row [] (println (:name row))))
John Doe
Melissa Swift
Tom Swift
Harry Potter

(with-cabinet params (with-query-results row [[:sort :name]] (println (:name row))))
Harry Potter
John Doe
Melissa Swift
Tom Swift

(with-cabinet params (with-query-results row [[:sort :name] [:order SORT-TEXT-DESC]] (println (:name row))))
Tom Swift
Melissa Swift
John Doe
Harry Potter

(with-cabinet params (with-query-results row [[:sort :name] [:order SORT-TEXT-DESC] [:limit 1]] (println (:name row))))
Tom Swift
</pre>
<h3>Lower Level</h3>
<p>Depending on your application, it might not be convenient to have to bracket everything with with-cabinet, since that means an open and close of the cabinet.  You can also use the lower level open-cabinet and close-cabinet calls, along with the &#8220;with&#8221; statement.  This is also an easier way to use it at the command line.  For example:</p>
<pre class="brush: php">
(def test-database (open-cabinet { :filename &quot;test-open.tokyo&quot; :mode (+ OWRITER OCREAT) }))
(with test-database (put-value &quot;1&quot; &quot;one&quot;))
(with test-database (get-value &quot;1&quot;))
(with test-database (print (primary-keys)))
(close-cabinet test-database)
</pre>
<h3>Miscellaneous</h3>
<p>Use (primary-keys) to return a lazy list of primary keys.</p>
<pre class="brush: php">
(with-cabinet { :filename &quot;test.tokyo&quot; :mode (+ OWRITER OCREATE) :type :table }
    (print (primary-keys)))
</pre>
<h3>Links</h3>
<ul>
<li><a href="http://tokyocabinet.sourceforge.net/" onclick="javascript:pageTracker._trackPageview('/outbound/article/tokyocabinet.sourceforge.net');">Tokyo Cabinet</a></li>
<li><a href="http://tokyocabinet.sourceforge.net/javadoc/" onclick="javascript:pageTracker._trackPageview('/outbound/article/tokyocabinet.sourceforge.net');">Tokyo Cabinet / Java API</a></li>
</ul>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/tokyo-cabinet-api-for-clojure/feed</wfw:commentRss>
		<slash:comments>3</slash:comments>
		</item>
		<item>
		<title>Posting To Wordpress From Git</title>
		<link>http://www.brool.com/index.php/posting-to-wordpress-from-git</link>
		<comments>http://www.brool.com/index.php/posting-to-wordpress-from-git#comments</comments>
		<pubDate>Mon, 27 Jul 2009 20:57:20 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[python]]></category>
		<category><![CDATA[git]]></category>
		<category><![CDATA[wordpress]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=302</guid>
		<description><![CDATA[I&#8217;ve found Wordpress to be pretty decent, aside from the security updates every other week, but for me writing is a very spur of the moment thing;  I prefer to be able to go into Emacs and just immediately type anything without having to log into my blog, create a new post, and then [...]]]></description>
			<content:encoded><![CDATA[<p>I&#8217;ve found Wordpress to be pretty decent, aside from the security updates every other week, but for me writing is a very spur of the moment thing;  I prefer to be able to go into Emacs and just immediately type anything without having to log into my blog, create a new post, and then suffer through a web editor.  Basically, I want to do it in Emacs!  Now!  And maybe I&#8217;m offline!</p>
<p>So, I wrote a tiny little program to help facilitate using git and Wordpress together through the XMLRPC API, and it&#8217;s helped me write&#8230; well, if not <i>more</i> than at least <i>less painfully</i>.</p>
<h3>Setting Up</h3>
<p>Assuming that your blog is set up at http://www.yourblog.com (you can create an account at wordpress.com to test this out), all you&#8217;ll need to do is:</p>
<pre class="brush: php">
-- make a directory for the blog
mkdir blog
chdir blog

-- download everything
python wp.py download --user=yourname --password=yourpass --url=http://www.yourblog.com/xmlrpc.php
(wait a bit)
git init
git add .
git commit -m &quot;first version&quot;

-- now set up so we don&#039;t have to specify --user, --password, and --url every time (optional)
git wp config wp.url http://www.yourblog.com/xmlrpc.php
git wp config wp.user yourname
git wp config wp.password yourpass
</pre>
<p>The files are downloaded in the appropriate YYYY/MM directories, with the draft directory being used for all of your unpublished drafts.</p>
<p>All the drafts are stored in plain text, but you&#8217;ll see some lines starting with periods &#8212; these are various Wordpress variables that are associated with the file.  You can change them, as well;  for example, to change the title of the post, just change the line that begins with &#8220;.title&#8221;. </p>
<h3>Seeing What&#8217;s Different</h3>
<p>You can use the status command to see differences between the local file system and your blog.</p>
<pre class="brush: php">
python wp.py status
</pre>
<h3>Updating From The Blog</h3>
<p>If you&#8217;ve made changes through the web interface and you&#8217;d like to bring them down, you don&#8217;t have to download everything again, but can instead just update.</p>
<pre class="brush: php">
python wp.py update
</pre>
<h3>Posting/Editing</h3>
<p>If you&#8217;d like to edit a post, just edit it, and then use wp post to push it back to the blog:</p>
<pre class="brush: php">
python wp.py post changed-file
</pre>
<p>To create a new post, just create a new file in the draft folder &#8212; I like to specify the .title and .wp_slug parameters, as well &#8212; and then post it.  You can also publish it by changing the .post_status line from draft to publish.</p>
<h3>Gotchas</h3>
<p>While this program <i>requires</i> git, it doesn&#8217;t automatically check anything in &#8212; so you&#8217;ll need to make sure you do git add / git commit or whatnot as necessary.</p>
<p>There are also some gotchas due to the fact that the filename can change on you.  There are cases where the filename that will be brought down is different then the one that you send up:</p>
<ul>
<li>You post a file without a .title or .wp_slug line</li>
<li>You post a file with a different file name than the slug that is generated (i.e., &#8220;my-first-draft&#8221; when the title is actually &#8220;my final draft&#8221;)</li>
<li>Something moves from &#8220;draft&#8221; to &#8220;publish&#8221;
</ul>
<p>When you see a message of the form &#8220;changed: fn1 -> fn2&#8243;, it means that a rename has occurred, and you&#8217;ll need to do the git rm/git add or git mv by hand.</p>
<h3>Source</h3>
<p><a href="http://github.com/brool/git-wordpress/tree/master" onclick="javascript:pageTracker._trackPageview('/outbound/article/github.com');">Source is available on github</a>.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/posting-to-wordpress-from-git/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Hacks: Python Calling PHP</title>
		<link>http://www.brool.com/index.php/hacks-python-calling-php</link>
		<comments>http://www.brool.com/index.php/hacks-python-calling-php#comments</comments>
		<pubDate>Wed, 22 Jul 2009 00:57:26 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[bridge]]></category>
		<category><![CDATA[hacks]]></category>
		<category><![CDATA[php]]></category>
		<category><![CDATA[python]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=313</guid>
		<description><![CDATA[(This is almost too stupid to post, but on the off chance that someone actually needs something like this&#8230;) 
I needed to interface with a bunch of data that had PHP wrapper classes, and needed a quick way of being able to interface with PHP from Python.  (At this point, you might find it [...]]]></description>
			<content:encoded><![CDATA[<p>(This is almost too stupid to post, but on the off chance that someone actually needs something like this&#8230;) </p>
<p>I needed to interface with a bunch of data that had PHP wrapper classes, and needed a quick way of being able to interface with PHP from Python.  (At this point, you might find it hard to believe that the PHP wrapper classes were worth trying to reuse, but the wrapper classes took care of partitioning and caching and everything, so it seemed silly to not reuse them).  I considered using the PHP API and ctypes to make a Python to PHP bridge , but then decided that was <i>entirely</i> too much work, so I just hacked together a stupid class that invoked PHP with arbitrary code and returned it in a number of ways.</p>
<h3>Basic usage</h3>
<p>Create the PHP class (giving it an optional prefix and postfix &#8212; prefix is the most useful, as it allows you to specify requires), and then invoke a code block with get_raw, get, or get_one.   Note that every &#8220;call&#8221; into PHP will create and destroy a PHP process.</p>
<p>Some examples:</p>
<h3>Reading raw input</h3>
<pre class="brush: python">
php = PHP(&quot;require &#039;../code/private/common.php&#039;;&quot;)
code = &quot;&quot;&quot;for ($i = 1; $i &lt;= 10; $i++) { echo &quot;$i\n&quot;; }&quot;&quot;&quot;
print php.get_raw(code)
</pre>
<p>will output a string containing the numbers &#8220;1&#8243;..&#8221;10&#8243;</p>
<h3>Reading one big JSON value</h3>
<pre class="brush: python">
php = PHP(&quot;require &#039;../code/private/common.php&#039;;&quot;)
code = &quot;&quot;&quot;
$a = array();
for ($i = 1; $i &lt;= 10; $i++) { $a[] = $i; }
echo json_encode($a);&quot;&quot;&quot;
print php.get(code)
</pre>
<p>This code would return a Python list with the numbers 1..10.</p>
<h3>Reading many JSON values</h3>
<pre class="brush: python">
    php = PHP(&quot;require &#039;../code/private/common.php&#039;;&quot;)
    code = &quot;&quot;&quot;
    for ($i = 1; $i &lt;= 10; $i++) {
        echo json_encode(array($i =&gt; $i * $i)) . &quot;\n&quot;;
    }&quot;&quot;&quot;
    for row in php.get_one(code):
        print row
</pre>
<p>Given a PHP snippet that returns one JSON value per line, iterate through them as Python values.</p>
<p>The actual code (also on <a href="http://github.com/brool/util/blob/master/php.py" onclick="javascript:pageTracker._trackPageview('/outbound/article/github.com');">Github</a>):</p>
<pre class="brush: python">
import popen2
import simplejson as json

class PHP:
    &quot;&quot;&quot;This class provides a stupid simple interface to PHP code.&quot;&quot;&quot;

    def __init__(self, prefix=&quot;&quot;, postfix=&quot;&quot;):
        &quot;&quot;&quot;prefix = optional prefix for all code (usually require statements)
        postfix = optional postfix for all code
        Semicolons are not added automatically, so you&#039;ll need to make sure to put them in!&quot;&quot;&quot;

        self.prefix = prefix
        self.postfix = postfix

    def __submit(self, code):
        (out, inp) = popen2.popen2(&quot;php&quot;)
        print &gt;&gt;inp, &quot;&lt;? &quot;
        print &gt;&gt;inp, self.prefix
        print &gt;&gt;inp, code
        print &gt;&gt;inp, self.postfix
        print &gt;&gt;inp, &quot; ?&gt;&quot;
        inp.close()
        return out

    def get_raw(self, code):
        &quot;&quot;&quot;Given a code block, invoke the code and return the raw result as a string.&quot;&quot;&quot;
        out = self.__submit(code)
        return out.read()

    def get(self, code):
        &quot;&quot;&quot;Given a code block that emits json, invoke the code and interpret the result as a Python value.&quot;&quot;&quot;
        out = self.__submit(code)
        return json.loads(out.read())

    def get_one(self, code):
        &quot;&quot;&quot;Given a code block that emits multiple json values (one per line), yield the next value.&quot;&quot;&quot;
        out = self.__submit(code)
        for line in out:
            line = line.strip()
            if line:
                yield json.loads(line)
</pre>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/hacks-python-calling-php/feed</wfw:commentRss>
		<slash:comments>2</slash:comments>
		</item>
		<item>
		<title>Recovering From A &#8211;hard Reset In Git</title>
		<link>http://www.brool.com/index.php/recovering-from-a-hard-reset-in-git</link>
		<comments>http://www.brool.com/index.php/recovering-from-a-hard-reset-in-git#comments</comments>
		<pubDate>Sun, 19 Apr 2009 06:37:09 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[git]]></category>
		<category><![CDATA[hard]]></category>
		<category><![CDATA[recovering]]></category>
		<category><![CDATA[reset]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=303</guid>
		<description><![CDATA[I was switching between git repositories the other day, and managed to do a &#8220;git reset &#8211;hard HEAD^&#8221; in the wrong repository.  Which wasn&#8217;t bad, since I had most of the files already open in Emacs&#8230; but then Emacs calmly told me that it was re-reading the files from disk.
But, git had everything still [...]]]></description>
			<content:encoded><![CDATA[<p>I was switching between git repositories the other day, and managed to do a &#8220;git reset &#8211;hard HEAD^&#8221; in the wrong repository.  Which wasn&#8217;t bad, since I had most of the files already open in Emacs&#8230; but then Emacs calmly told me that it was re-reading the files from disk.</p>
<p>But, git had everything still around &#8212; it turns out to be pretty easy to get it back.  The magic command turned out to be git reflog.</p>
<div class="codesnip-container" >$ git reflog<br />
aba2b93&#8230; HEAD@{0}: reset &#8211;hard HEAD^<br />
28a0c01&#8230; HEAD@{1}: commit: more work on pre-receive<br />
1c4a3af&#8230; HEAD@{2}: merge tmp: Fast forward<br />
84d69cb&#8230; HEAD@{3}: checkout: moving to commit_hooks<br />
1c4a3af&#8230; HEAD@{4}: commit: commit hooks<br />
a489ebd&#8230; HEAD@{5}: checkout: moving to tmp<br />
a489ebd&#8230; HEAD@{6}: checkout: moving to a489ebd</div>
<p>So I had lost everything in HEAD@{1}, but you can get it back by just checking out that particular commit.</p>
<div class="codesnip-container" >$ git checkout HEAD@{1}<br />
Note: moving to &#8220;28a0c01&#8243; which isn&#8217;t a local branch<br />
If you want to create a new branch from this checkout, you may do so<br />
(now or later) by using -b with the checkout command again. Example:<br />
  git checkout -b <new_branch_name><br />
HEAD is now at 28a0c01&#8230; commit: more work on pre-receive</p>
<p>$ git checkout -b tmp<br />
&#8230; do whatever you need to do to get tmp to the right state &#8230;</p>
<p>$ git checkout master<br />
$ git merge tmp</p></div>
<p>Note that if I didn&#8217;t need to fiddle around with stuff, but just had wanted everything in the commit, I could just have merged the entire commit:</p>
<div class="codesnip-container" >$ git merge HEAD@{1}</div>
<p>&#8230; and that would have brought everything back to the state I needed.</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/recovering-from-a-hard-reset-in-git/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Stupid Haskell Tricks</title>
		<link>http://www.brool.com/index.php/stupid-haskell-tricks</link>
		<comments>http://www.brool.com/index.php/stupid-haskell-tricks#comments</comments>
		<pubDate>Mon, 13 Apr 2009 10:25:30 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[oo]]></category>
		<category><![CDATA[stupid]]></category>
		<category><![CDATA[tricks]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=294</guid>
		<description><![CDATA[Let&#8217;s say that you really, really want some notion of objected oriented programming.  So let&#8217;s make a class that represents a name, and some simple method calls on it:

data S = S { name :: String } deriving (Show)
firstname s = (words (name s))!!0
lastname  s = (words (name s))!!1

But, dammit, you want to [...]]]></description>
			<content:encoded><![CDATA[<p>Let&#8217;s say that you really, <i>really</i> want some notion of objected oriented programming.  So let&#8217;s make a class that represents a name, and some simple method calls on it:</p>
<pre class="brush: php">
data S = S { name :: String } deriving (Show)
firstname s = (words (name s))!!0
lastname  s = (words (name s))!!1
</pre>
<p>But, dammit, you want to invoke it like you would in C++.  So define a function:</p>
<pre class="brush: php">
*Main&gt; let (--&gt;) x f = f x
*Main&gt; let test = S &quot;George Washington&quot;
*Main&gt; test --&gt; firstname
&quot;George&quot;
*Main&gt; test --&gt; lastname
&quot;Washington&quot;
</pre>
<p>(It&#8217;s tempting to use `.`, but it conflicts with the Prelude.  Also note that you could define it as &#8220;(&#8211;>) = flip ($)&#8221;).  But what if it takes more than one parameter?</p>
<pre class="brush: php">
*Main&gt; let flip_concat t s = intercalate t $ reverse.words $ name s
*Main&gt; test --&gt; flip_concat &quot;, &quot;
&quot;Washington, George&quot;
*Main&gt; test --&gt; flip_concat(&quot;, &quot;)
&quot;Washington, George&quot;
</pre>
<p>&#8230; although you might not like that anything can be applied to (&#8211;>).</p>
<pre class="brush: php">
*Main&gt; [1,2,3] --&gt; length
3

class Deref a where
    (--&gt;) :: a -&gt; (a -&gt; b) -&gt; b
    x --&gt; f = f x 

instance Deref S

*Main&gt; [1,2,3] --&gt; length

&lt;interactive&gt;:1:0:
    No instance for (Deref [t])
      arising from a use of `--&gt;&#039; at &lt;interactive&gt;:1:0-17
    Possible fix: add an instance declaration for (Deref [t])
    In the expression: [1, 2, 3] --&gt; length
    In the definition of `it&#039;: it = [1, 2, 3] --&gt; length
</pre>
<p>You can even use tuple passing to make it look even more like a typical call.</p>
<pre class="brush: php">
*Main&gt; let pretty (pre, mid, post) s = pre ++ (firstname s) ++ mid ++ (lastname s) ++ post
*Main&gt; test --&gt; pretty (&quot;&lt;&quot;, &quot;, &quot;, &quot;&gt;&quot;)
&quot;&lt;George, Washington&gt;&quot;
</pre>
<p>&#8230; although that makes it harder to curry. </p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/stupid-haskell-tricks/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Haskell To Wordpress (Snippet)</title>
		<link>http://www.brool.com/index.php/haskell-to-wordpress-snippet</link>
		<comments>http://www.brool.com/index.php/haskell-to-wordpress-snippet#comments</comments>
		<pubDate>Fri, 10 Apr 2009 08:25:00 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[haxr]]></category>
		<category><![CDATA[wordpress]]></category>
		<category><![CDATA[xmlrpc]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=291</guid>
		<description><![CDATA[A small snippet of code that demonstrates calling into a Wordpress XML-RPC server with Haskell and HaxR.

import qualified Data.Map as Map
import Data.Maybe
import Network.XmlRpc.Client
import Network.XmlRpc.Internals

server = &#34;http://yourserver.wordpress.com/xmlrpc.php&#34;

-- extract multiple posts from the XML response
extract :: Value -&#62; [Map String Value]
extract xmlresp =
    let ValueArray rs = xmlresp in
    map (\v [...]]]></description>
			<content:encoded><![CDATA[<p>A small snippet of code that demonstrates calling into a Wordpress XML-RPC server with Haskell and <a href="http://www.haskell.org/haxr/" onclick="javascript:pageTracker._trackPageview('/outbound/article/www.haskell.org');">HaxR</a>.</p>
<pre class="brush: php">
import qualified Data.Map as Map
import Data.Maybe
import Network.XmlRpc.Client
import Network.XmlRpc.Internals

server = &quot;http://yourserver.wordpress.com/xmlrpc.php&quot;

-- extract multiple posts from the XML response
extract :: Value -&gt; [Map String Value]
extract xmlresp =
    let ValueArray rs = xmlresp in
    map (\v -&gt; case v of
                  ValueStruct vs -&gt; Map.fromList vs
                  _              -&gt; Map.fromList []) rs

getRecentPosts :: Int -&gt; [Char] -&gt; [Char] -&gt; Int -&gt; IO Value
getRecentPosts = remote server &quot;metaWeblog.getRecentPosts&quot;

-- print out the five most recent posts
main = do result &lt;- getRecentPosts 1 &quot;yourname&quot; &quot;yourpass&quot; 5
          let posts = extract result
          mapM_ (\p -&gt; print $ fromJust $ Map.lookup &quot;title&quot; p) posts
</pre>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/haskell-to-wordpress-snippet/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Haskell Performance: Array Creation</title>
		<link>http://www.brool.com/index.php/haskell-performance-array-creation</link>
		<comments>http://www.brool.com/index.php/haskell-performance-array-creation#comments</comments>
		<pubDate>Mon, 30 Mar 2009 03:00:20 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[performance]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=274</guid>
		<description><![CDATA[Ran into another interesting performance problem while converting a small test program over to Haskell. Let&#8217;s say that you want to walk through every line of a text file, collate character frequencies, and return anything that maps to a particular frequency.  For purposes of explanation we&#8217;ll do something really silly like look for lines [...]]]></description>
			<content:encoded><![CDATA[<p>Ran into another interesting performance problem while converting a small test program over to Haskell. Let&#8217;s say that you want to walk through every line of a text file, collate character frequencies, and return anything that maps to a particular frequency.  For purposes of explanation we&#8217;ll do something really silly like look for lines with 10 capital &#8216;A&#8217;s.</p>
<pre class="brush: php">
{-# OPTIONS -XBangPatterns #-}
import IO
import System
import Data.Word
import Data.Array.Unboxed
import Control.Monad.ST
import Data.Array.ST
import qualified Data.ByteString as B
import qualified Data.ByteString.Internal as BI
import qualified Data.ByteString.Char8 as C

counts&#039; !line = do arr &lt;- newArray (0,255) 0 :: ST s (STUArray s Word8 Int)
                   -- collate character counts here
                   return arr
counts !line = runSTUArray (counts&#039; line)

hit !line = let freq = counts line in freq!65 == 10

main =
    do args &lt;- getArgs
       f &lt;- openFile &quot;wordlist&quot; ReadMode
       text &lt;- B.hGetContents f
       print $ length $ filter hit (C.lines text)
</pre>
<p>This is fast (0.07s on 300K test file, compiled with -O2 on a Macbook Pro), but there&#8217;s no actual collation going on.  It suddenly becomes two magnitudes slower as soon as you start to do anything based on the line:</p>
<pre class="brush: php">
-- version 1 : 9.5 seconds
counts&#039; !line = do arr &lt;- newArray (0,255) 0 :: ST s (STUArray s Word8 Int)
                   readArray arr (B.head line) &gt;&gt;= \v -&gt; writeArray arr (B.head line) (v+1)
                   return arr
counts !line = runSTUArray (counts&#039; line)
</pre>
<p>.. equals 9.54 seconds just when you collate the first character of the string, and led me to believe that ByteStrings were slow, especially since a constant change to the array was fast (0.07 seconds):</p>
<pre class="brush: php">
-- version 2 : 0.07 seconds
counts&#039; !line = do arr &lt;- newArray (0,255) 0 :: ST s (STUArray s Word8 Int)
                   readArray arr 0 &gt;&gt;= \v -&gt; writeArray arr 0 (v+1)
                   return arr
</pre>
<p>(Here I&#8217;ll elide the hours of me messing around with profiling and whatnot to try and figure out why B.head was so slow, or how to make B.foldl&#8217; update a state variable, or sprinkling strictness bangs all over the place, or the other tons of false trails that I went down.)</p>
<p>It turns out that the slow portion in all of this is the newArray, not the character collation itself, which can be seen in the profile if the array creation is moved into its own routine and we look at the profile:</p>
<pre class="brush: php">
-- version 3
-- compile with: ghc -package bytestring stuarray.hs -prof -auto-all -O2 -o stuarray.out
-- run with: ./stuarray.out +RTS -p
initial_array = do arr &lt;- newArray (0,255) 0 :: ST s (STUArray s Word8 Int)
                   return arr

counts&#039; !line = do arr &lt;- initial_array
                   let ix = B.head line
                   readArray arr ix &gt;&gt;= \v -&gt; writeArray arr ix (v+1)
                   return arr
counts !line = runSTUArray (counts&#039; line)
</pre>
<p>&#8230; and the relevant part of the profile:</p>
<pre>
MAIN                     MAIN                     1           0   0.0    0.0   100.0  100.0
 main                    Main                   240           1   0.7    0.3   100.0  100.0
  hit                    Main                   242      335075   0.0    0.0    99.3   99.7
   counts                Main                   243      335075   0.0    0.2    99.3   99.7
    counts'              Main                   244      335075   0.0    0.0    99.3   99.5
     initial_array       Main                   245      335075  99.3   99.5    99.3   99.5
</pre>
<p>Which brings up two interesting points:</p>
<ul>
<li>The Haskell optimizer was so smart that it was able to figure out that the code in version 2 built a constant array&#8230; and so only called the newArray once.  (Confirmed with a profile).</li>
<li>New array creation seems to be so slow that it <i>dominates a benchmark that has file I/O.</i></li>
</ul>
<p>The Ocaml version took about 0.720 seconds (Ocaml version below), compared to Haskell time of about 8.5 seconds.  Reducing the array size to 128 in both cases reduced it to 0.112 seconds for Ocaml and 4.3 seconds in Haskell.</p>
<table border="1px dotted">
<tr>
<th>Array size</th>
<th>Ocaml</th>
<th>Haskell</th>
</tr>
<tr>
<td>128</td>
<td>0.112</td>
<td>4.3</td>
</tr>
<tr>
<td>255</td>
<td>0.184</td>
<td>8.5</td>
</tr>
<tr>
<td>256</td>
<td>0.720</td>
<td>8.5</td>
</tr>
</table>
<p>Note the discontinuity in Ocaml between 255 and 256 elements, which I find interesting.  The nice people in #haskell suggested that I stop constructing/destructing the array and instead just null it out between each line, and it turned out that the best way to do that was just to thaw a starter array.</p>
<pre class="brush: php">
-- version 4: 0.11 seconds
initial_array = listArray (0,255) (repeat 0) :: UArray Word8 Int

counts&#039; !line = do arr &lt;- thaw initial_array
                   let ix = B.head line
                   readArray arr ix &gt;&gt;= \v -&gt; writeArray arr ix (v+1)
                   return arr
counts !line = runSTUArray (counts&#039; line)
</pre>
<p>This is still kind of strange to me (because an object is still getting constructed/destructed &#8212; thaw guarantees a copy) but you can&#8217;t argue with a performance increase.  (Interestingly, using Array.copy or Array.fill in Ocaml is <i>slower</i> than just using Array.make).  Final times?  0.11 seconds in Haskell vs. the best of <strike>0.720 second</strike> UPDATED: 0.12 seconds in Ocaml&#8230; and the Haskell version is just 50% slower than a C implementation with a gratuitous calloc instead of a memset. </p>
<p><b>UPDATE</b>:  An pointed out that zeroing the Ocaml array with a for loop is much faster than Array.copy or Array.fill, bringing it to about the same speed as Haskell.</p>
<p>Lessons learned?</p>
<ul>
<li>Performance is a treacherous mistress</li>
<li>The Haskell optimizer is awesome but you have to be wary when trying to narrow down performance problems</li>
<li>#haskell is always full of useful suggestions</li>
<li>Array creation seems to be slow enough that alternatives should be explored.</li>
</ul>
<pre class="brush: php">
open Char
open String

let all_lines fn filename =
    let chan = open_in filename in
        try
            while true do
                let line = input_line chan in
                    fn line
            done
        with End_of_file -&gt;
            close_in chan

let initial_array = Array.make 256 0

let count line =
    let freq = initial_array in
    let ix = int_of_char line.[0] in
        for i = 0 to 255 do freq.(i) &lt;- 0 done;
        freq.(ix) &lt;- freq.(ix) + 1;
        freq

let hit line =
    let freq = count line in
        freq.(65) = 10

let _ =
    let linecount = ref 0 in
        all_lines (fun line -&gt; if hit line then linecount := !linecount + 1 else ()) &quot;wordlist&quot;;
        print_int !linecount
</pre>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/haskell-performance-array-creation/feed</wfw:commentRss>
		<slash:comments>4</slash:comments>
		</item>
		<item>
		<title>Haskell Performance: Lowercase</title>
		<link>http://www.brool.com/index.php/haskell-performance-lowercase</link>
		<comments>http://www.brool.com/index.php/haskell-performance-lowercase#comments</comments>
		<pubDate>Sun, 29 Mar 2009 02:05:25 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[performance]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=266</guid>
		<description><![CDATA[I was trying to track down some issues with some text processing programs that I was writing in Haskell, and ran into an interesting problem.  I made one small change and my program ended up being 5 times slower, and I had to backtrack to try and find out what it was. So, given [...]]]></description>
			<content:encoded><![CDATA[<p>I was trying to track down some issues with some text processing programs that I was writing in Haskell, and ran into an interesting problem.  I made one small change and my program ended up being 5 times slower, and I had to backtrack to try and find out what it was. So, given a simple Haskell program that sees if a word is in a wordlist:</p>
<pre class="brush: php">
import IO
import System
import qualified Data.ByteString as B
import qualified Data.ByteString.Internal as BI
import qualified Data.ByteString.Char8 as C

main = do args &lt;- getArgs
          let searchfor = C.pack $ head args
          f &lt;- openFile &quot;wordlist&quot; ReadMode
          text &lt;- B.hGetContents f
          print $ length $ filter ((==) searchfor) (C.lines text)
</pre>
<p>To search a smallish list of about 300K words takes 0.040 seconds on my computer, compared to 0.200 seconds for Python and 0.210 seconds for a naive Haskell implementation that is not using ByteStrings.  However, let&#8217;s just add lowercase to the equation:</p>
<pre class="brush: php">
import IO
import System
import Data.Char
import qualified Data.ByteString as B
import qualified Data.ByteString.Internal as BI
import qualified Data.ByteString.Char8 as C

main = do args &lt;- getArgs
          let searchfor = C.pack $ head args
          f &lt;- openFile &quot;wordlist&quot; ReadMode
          text &lt;- B.hGetContents f
          print $ length $ filter (\x -&gt; (C.map toLower x) == searchfor) (C.lines text)
</pre>
<p>Suddenly, the ByteString version becomes about 30% <i>slower</i> than the naive version &mdash; 0.337 seconds vs. 0.251 seconds &mdash; and is even slower than the Python version.  What the heck is going on here?  Trying an empty map (i.e., C.map id x) resulted in something fast, so I&#8217;m suspecting that the lowercase function itself is slow.</p>
<p>Unfortunately, there doesn&#8217;t seem to be a lowercase available in ByteString; at the moment it seems that you need to set up your own ctype table and use that.</p>
<pre class="brush: php">
import IO
import System
import Data.Char
import Data.Word
import Data.Array.Unboxed
import qualified Data.ByteString as B
import qualified Data.ByteString.Internal as BI
import qualified Data.ByteString.Char8 as C

ctype_lower = listArray (0,255) (map (BI.c2w . toLower) [&#039;\0&#039;..&#039;\255&#039;]) :: UArray Word8 Word8
lowercase = B.map (\x -&gt; ctype_lower!x)

main = do args &lt;- getArgs
          let searchfor = C.pack $ head args
          f &lt;- openFile &quot;wordlist&quot; ReadMode
          text &lt;- B.hGetContents f
          print $ length $ filter (\x -&gt; (lowercase x) == searchfor) (C.lines text)
</pre>
<p>&#8230; which turns out to run really quickly at 0.070 seconds, about the same as a C program doing the same task.</p>
<p><b>Update</b>:  See dons comments below &#8212; Char is operating on Unicode, which makes it slow.  I wonder if a ctype.h-type library for ByteString makes sense?</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/haskell-performance-lowercase/feed</wfw:commentRss>
		<slash:comments>1</slash:comments>
		</item>
		<item>
		<title>Using MissingPy</title>
		<link>http://www.brool.com/index.php/using-missingpy</link>
		<comments>http://www.brool.com/index.php/using-missingpy#comments</comments>
		<pubDate>Fri, 20 Mar 2009 02:15:00 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[python]]></category>
		<category><![CDATA[imap]]></category>
		<category><![CDATA[missingpy]]></category>
		<category><![CDATA[tutorial]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=209</guid>
		<description><![CDATA[For comparison purposes, I was rewriting the silly little e-mail digest program in Haskell, using Python libraries for the IMAP interface (it&#8217;s available on Github). It&#8217;s hard to beat Python&#8217;s amazing collection of libraries.  Cabal / hackage isn&#8217;t bad, but it doesn&#8217;t yet approach Python&#8217;s &#8220;batteries included&#8221; philosophy and ease of use.  Anyway, [...]]]></description>
			<content:encoded><![CDATA[<p>For comparison purposes, I was rewriting the <a href="http://www.brool.com/index.php/creating-mail-digests-with-python-and-imap" >silly little e-mail digest program</a> in Haskell, using Python libraries for the IMAP interface (it&#8217;s <a href="http://github.com/brool/digest/tree/master" onclick="javascript:pageTracker._trackPageview('/outbound/article/github.com');">available on Github</a>). It&#8217;s hard to beat Python&#8217;s amazing collection of libraries.  Cabal / hackage isn&#8217;t bad, but it doesn&#8217;t yet approach Python&#8217;s &#8220;batteries included&#8221; philosophy and ease of use.  Anyway, I couldn&#8217;t find an IMAP library for Haskell, so decided instead to try <a href="http://hackage.haskell.org/cgi-bin/hackage-scripts/package/MissingPy" onclick="javascript:pageTracker._trackPageview('/outbound/article/hackage.haskell.org');">MissingPy</a> to interface into the Python IMAP library.  A quick overview/tutorial:</p>
<h3>Installing MissingPy</h3>
<p>I had an issue using Cabal to install MissingPy into my GHC 6.10 installation (Mac OS X).  I went into the directory that had been unpacked and modified Setup.hs:</p>
<pre class="brush: php">
import Distribution.PackageDescription
import Distribution.PackageDescription.Parse  -- added this line
import Distribution.Simple
</pre>
<p>A cabal configure, build, and install of the package then installed everything.</p>
<h3>Basic Usage</h3>
<p>It&#8217;s easiest to play around with MissingPy in ghci.  Before you do anything you&#8217;ll need to initialize the interpreter with py_initialize and import any necessary modules with pyImport.  You can test by using pyRun_SimpleString:</p>
<pre class="brush: php">
# :m Python.Interpreter Python.Objects Python.Utils Python.Exceptions
# py_initialize
# pyRun_SimpleString &quot;print &#039;hello&#039;&quot;
hello
</pre>
<p>The simplest useful way to execute python code is to use pyRun_String.  For example:</p>
<pre class="brush: php">
-- add 1 and 2 in Python
-- can also use Py_file_input or Py_single_input for different handling of the context
addem = pyRun_String &quot;1+2&quot; Py_eval_input [] &gt;&gt;= fromPyObject :: IO Integer
</pre>
<p>There are also the callByName and pyObject_Call methods for more complicated scenarios.</p>
<pre class="brush: php">
callByName :: String            -- ^ Object\/function name
           -&gt; [PyObject]        -- ^ List of non-keyword parameters
           -&gt; [(String, PyObject)] -- ^ List of keyword parameters
           -&gt; IO PyObject

pyObject_Call :: PyObject       -- ^ Object to call
              -&gt; [PyObject]     -- ^ List of non-keyword parameters (may be empty)
              -&gt; [(String, PyObject)] -- ^ List of keyword parameters (may be empty)
              -&gt; IO PyObject    -- ^ Return value

-- example 1: create an IMAP instance
imap &lt;- callByName &quot;imaplib.IMAP4_SSL&quot; [imap_hostname] []

-- call &quot;foo.bar(p1,p2)&quot;
bar &lt;- getattr foo &quot;bar&quot;
result &lt;- pyObject_Call bar [p1,p2] []
</pre>
<h3>Manipulating Python Objects</h3>
<p>The fromPyObject and toPyObject handle marshaling of objects from Haskell to Python and vice versa.  There are some handy functions for doing common operations on Python objects that are especially useful from the REPL: reprOf (like Python repr), strOf (Python str), showPyObject (shows the type and repr), and dirPyObject (like the Python dir()).</p>
<pre class="brush: php">
# g &lt;- pyRun_String &quot;(1,2,&#039;hello&#039;)&quot; Py_eval_input []
# showPyObject g
&quot;&lt;type &#039;tuple&#039;&gt;: (1, 2, &#039;hello&#039;)&quot;
# reprOf g
&quot;(1, 2, &#039;hello&#039;)&quot;
# strOf g
&quot;(1, 2, &#039;hello&#039;)&quot;
# dirPyObject g
[&quot;__add__&quot;,&quot;__class__&quot;,&quot;__contains__&quot;,&quot;__delattr__&quot;,&quot;__doc__&quot;,&quot;__eq__&quot;,&quot;__ge__&quot;,
&quot;__getattribute__&quot;,&quot;__getitem__&quot;,&quot;__getnewargs__&quot;,&quot;__getslice__&quot;,&quot;__gt__&quot;,
&quot;__hash__&quot;,&quot;__init__&quot;,&quot;__iter__&quot;,&quot;__le__&quot;,&quot;__len__&quot;,&quot;__lt__&quot;,&quot;__mul__&quot;,&quot;__ne__&quot;,
&quot;__new__&quot;,&quot;__reduce__&quot;,&quot;__reduce_ex__&quot;,&quot;__repr__&quot;,&quot;__rmul__&quot;,&quot;__setattr__&quot;,&quot;__str__&quot;]
</pre>
<h3>Dealing with Data</h3>
<p>Tuples look like lists when they are returned.  There is no conversion of tuples in the toPyObject call, so you&#8217;ll need to just convert a list and then convert it to a tuple with pyList_AsTuple.  Passing &#8220;None,&#8221; &#8220;True,&#8221; or &#8220;False&#8221; is trickier; the only way I found to do it was create an instance of the value and use it in subsequent calls.</p>
<pre class="brush: php">
# a
[1,2]
# b &lt;- toPyObject a
# reprOf b
&quot;[1L, 2L]&quot;
# pyList_AsTuple b &gt;&gt;= reprOf
&quot;(1L, 2L)&quot;

-- get &quot;True,&quot; &quot;False,&quot; and &quot;None&quot;
none &lt;- pyRun_String &quot;None&quot; Py_eval_input []
pyTrue &lt;- pyRun_String &quot;True&quot; Py_eval_input []
pyFalse &lt;- pyRun_String &quot;False&quot; Py_eval_input []

-- try it out
# r &lt;- pyRun_String &quot;1==1&quot; Py_eval_input []
# r == pyTrue
True
</pre>
<h3>Passing Haskell Objects</h3>
<p>If you want to call into functions without having to deal with Python objects, there are a couple of calls that automatically marshal the objects back and forth for you (all suffixed with &#8220;Hs&#8221;), although they turn out to be less than useful in most situations, since a) the parameters passed in must all be the same type, and b) extracting most return objects from Python is painful.  </p>
<table border="1px solid" width="100%">
<tr>
<th>call</th>
<th>invoked upon</th>
<th>returns</th>
</tr>
<tr>
<td>callByNameHs</td>
<td>Object/function name</td>
<td>Haskell</td>
</tr>
<tr>
<td>pyObject_CallHs</td>
<td>PyObject</td>
<td>Haskell</td>
</tr>
<tr>
<td>pyObject_Hs</td>
<td>PyObject</td>
<td>Python</td>
</tr>
<tr>
<td>pyObject_RunHs</td>
<td>PyObject</td>
<td>nothing</td>
</tr>
<tr>
<td>callMethodHs</td>
<td>PyObject + method name</td>
<td>Haskell</td>
</tr>
<tr>
<td>runMethodHs</td>
<td>PyObject + method name</td>
<td>nothing</td>
</tr>
</table>
<p><br/></p>
<h3>Exceptions</h3>
<p>Python exceptions can be caught and handled;  probably the easiest default way to do this is to use handlePy in conjunction with the ex2ioerr handler, which will automatically print the exception and fail.</p>
<pre class="brush: php">
addem = handlePy exc2ioerror $
           do r &lt;- pyRun_String &quot;1/0&quot; Py_eval_input []
              fromPyObject r :: IO Integer

# addem
*** Exception: user error (Python &lt;type &#039;exceptions.ZeroDivisionError&#039;&gt;: integer division or modulo by zero)
</pre>
<p>another line added<br />
another line added</p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/using-missingpy/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Python to Haskell (String Functions)</title>
		<link>http://www.brool.com/index.php/python-to-haskell-string-functions</link>
		<comments>http://www.brool.com/index.php/python-to-haskell-string-functions#comments</comments>
		<pubDate>Thu, 26 Feb 2009 06:29:40 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[python]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=191</guid>
		<description><![CDATA[I will be updating this as I go&#8230;  but see also the Wikipedia page on string functions in various languages.
Joining a string list

-- Python:  &#34;,&#34;.join(lst)
-- either...
import Data.List
intercalate &#34;,&#34; lst
-- or...
import Data.List
concat (intersperse &#34;,&#34; lst)

Splitting on a string

-- a.split(ss)
-- You might need to get Data.List.Split from Cabal
import Data.List.Split
splitOn ss a
-- using regexes
import Text.Regex
splitRegex (mkRegex [...]]]></description>
			<content:encoded><![CDATA[<p>I will be updating this as I go&#8230;  but see also <a href="http://en.wikipedia.org/wiki/String_manipulation_algorithm" onclick="javascript:pageTracker._trackPageview('/outbound/article/en.wikipedia.org');">the Wikipedia page on string functions in various languages</a>.</p>
<p><b>Joining a string list</b></p>
<pre class="brush: php">
-- Python:  &quot;,&quot;.join(lst)
-- either...
import Data.List
intercalate &quot;,&quot; lst
-- or...
import Data.List
concat (intersperse &quot;,&quot; lst)
</pre>
<p><b>Splitting on a string</b></p>
<pre class="brush: php">
-- a.split(ss)
-- You might need to get Data.List.Split from Cabal
import Data.List.Split
splitOn ss a
-- using regexes
import Text.Regex
splitRegex (mkRegex ss) a
</pre>
<p><b>Does the string start with the prefix?</b></p>
<pre class="brush: php">
-- Python: a.startswith(b)
import Data.List
isPrefixOf b a
-- ByteString
import Data.ByteString
isPrefixOf b a
</pre>
<p><b>Does the string end with the suffix?</b></p>
<pre class="brush: php">
-- Python: a.endswith(b)
import Data.List
isSuffixOf b a
-- ByteString
import Data.ByteString
isSuffixOf b a
</pre>
<p><b>Does one string contain another?</b></p>
<pre class="brush: php">
-- Python: a.find(b) != -1
import Data.List
isInfixOf b a
-- ByteString
import Data.ByteString
isInfixOf b a
-- ByteString
import Data.ByteString
findSubstring b a -- returns Just int or Nothing
</pre>
<p><b>Reverse a string</b></p>
<pre class="brush: php">
-- Python: a[::-1]
reverse a
-- ByteString
import Data.ByteString
reverse bs
</pre>
<p><b>Access one character</b></p>
<pre class="brush: php">
-- Python: a[pos]
a !! pos    -- slow O(n)
-- ByteString
import Data.ByteString
index a pos
</pre>
<p><b>Where does one string contain another?</b></p>
<pre class="brush: php">
-- Python: a.find(b)
import Data.ByteString
findSubstring a b
</pre>
<p><b>Replace substrings</b></p>
<pre class="brush: php">
-- Python: b = a.replace(src,dest)
import Text.Regex
b = subRegex (mkRegex src) a dest
</pre>
<p><b>Replace regex, calling function on substitution</b></p>
<pre class="brush: php">
-- Python: b = re.sub(&quot;[0-9]+&quot;, lambda x: str(int(x.group(0)) + 1), a)
import Text.Regex (matchRegexAll, mkRegex)

subRegexFn fn re s = concat $ reverse $ sub s []
    where sub s accum = case matchRegexAll re s of
                            Nothing -&gt; s:accum
                            Just (pre, mid, post, _) -&gt; sub post $ (fn mid):pre:accum 

b = subRegexFn (read . (+ 1) . show) &quot;[0-9]+&quot; a
</pre>
<p><b>Strip leading/trailing spaces</b></p>
<pre class="brush: php">
-- Python: a.strip()
import Data.Char (isSpace)
trim      :: String -&gt; String
trim      = f . f
   where f = reverse . dropWhile isSpace
</pre>
<p><b>Loop through every line in stdin</b></p>
<pre class="brush: php">
-- Python:  loop through every line in stdin, applying a function
-- for line in sys.stdin:
--      print fn(line)
let main = interact (unlines . map fn . lines)
-- or...
let main = do { a &lt;- stdin; mapM_ print (map fn (lines a)); }
</pre>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/python-to-haskell-string-functions/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>State Monads in Haskell</title>
		<link>http://www.brool.com/index.php/state-monads-in-haskell</link>
		<comments>http://www.brool.com/index.php/state-monads-in-haskell#comments</comments>
		<pubDate>Tue, 24 Feb 2009 21:36:25 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[haskell]]></category>
		<category><![CDATA[haskell monad]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=169</guid>
		<description><![CDATA[I would like Haskell better if it didn&#8217;t do its best to make me feel stupid.  Tasks that are easy in other languages, such, say, maintaining some state or generating a random number, become difficult.  After banging my head on the State monad I finally arrived at a kind of understanding, which I [...]]]></description>
			<content:encoded><![CDATA[<p>I would like Haskell better if it didn&#8217;t do its best to make me feel stupid.  Tasks that are <i>easy</i> in other languages, such, say, maintaining some state or generating a random number, become difficult.  After banging my head on the State monad I finally arrived at a kind of understanding, which I put here so I can restore context in the future!</p>
<p>Presume that you&#8217;ve got a function that, given a list, returns a list of booleans corresponding to whether the value was the first occurrence in the list.  In Python it would look something like this: </p>
<pre class="brush: python">
def is_first(lst):
    found = set()
    r = []
    for item in lst:
        r.append(item not in found)
        found.add(item)
    return r
</pre>
<p>For example:</p>
<pre class="brush: python">
&gt;&gt;&gt; is_first([1,2,3,1,4])
[True, True, True, False, True]
</pre>
<p>The most simplistic way of converting this to Haskell would require using recursion for the looping, resulting in the following (non-tail-recursive) function:</p>
<pre class="brush: php">
first  lst = first&#039; lst []
first&#039; [] _ = []
first&#039; (h:t) state =
       if h `elem` found then False:(first&#039; t state)
       else True:(first&#039; t (h:state))
</pre>
<p>The first&#8217; function needs to &#8220;carry around&#8221; state as it loops around.  Now, say that the lookup function is more complicated than we thought, so we break it out into a separate function.  We have to pass around the state to all functions that access it, resulting in:</p>
<pre class="brush: php">
first  lst = first&#039; lst []
first&#039; [] _ = []
first&#039; (h:t) state =
       if (isfound h state) then False:(first&#039; t state)
       else True:(first&#039; t (h:state))

isfound h state = h `elem` state
</pre>
<p>Since isfound references the state, then it needs to be passed in explicitly.</p>
<p>I think that my main problem with understanding the State monad was that I kept wanting to treat the state as a global variable;  so, I was thinking of &#8220;s <- get" and "put s" as references to a global stored somewhere, which left me with the question of "where is the initial put that sets the state?"  Instead, though, you should think of "s <- get" and "put s" as references to an implicitly passed parameter. </p>
<p>The State Monad allows this particular pattern to be changed so that the state doesn't need to be explicitly passed.   Rewriting:</p>
<pre class="brush: php">
state_first lst = evalState (state_first&#039; lst) []
state_first&#039; []    = return []
state_first&#039; (h:t) = do state &lt;- get
                        let found = h `elem` state
                        put (if found then state else (h:state))
                        rest &lt;- state_first&#039; t
                        return $ (not found):rest
</pre>
<p>Basically, given a Haskell function, you can convert it into the state monad by:</p>
<ul>
<li>Removing the explicitly passed state</li>
<li>Changing all references to the state parameter to "param <- get"</li>
<li>Instead of recursively descending, use "put new-state-value"</li>
<li>Calling a state returns using "<-" to 'strip' the value</li>
</ul>
<p>Now, this doesn't seem more elegant, but note that if you have to break functionality out, the state parameter no longer needs to be explicitly passed:</p>
<pre class="brush: php">
state_first lst = evalState (state_first&#039; lst) []
state_first&#039; []    = return []
state_first&#039; (h:t) = do state &lt;- get
                        found &lt;- isfound h
                        put (if found then state else (h:state))
                        rest &lt;- state_first&#039; t
                        return $ (not found):rest

isfound h = do state &lt;- get
               return $ h `elem` state
</pre>
<p>UPDATED:  following a question on #haskell (which was very friendly, especially to a complete newcomer), the following more elegant ways of solving this came up:</p>
<pre class="brush: php">
-- using mapAccum
first lst = snd $ mapAccumL first&#039; [] lst
    where first&#039; acc x = (if found then acc else x:acc, not found)
              where found = x `elem` acc

-- with mapM (not exactly equivalent to example)
first lst = evalState first&#039; []
    where first&#039; = mapM (\a -&gt; do state &lt;- get; put (a:state); return $ not (a `elem` state)) lst

-- with mapM, equivalent to example
first lst = evalState first&#039; []
    where first&#039; = mapM isfound lst
          isfound a = do state &lt;- get
                         let found = a `elem` state
                         put (if found then state else (a:state))
                         return $ not found
</pre>
<div class="moreinfo">
<b>For more information:</b><br/><br />
<a href="http://www.haskell.org/haskellwiki/Roll_your_own_IRC_bot" onclick="javascript:pageTracker._trackPageview('/outbound/article/www.haskell.org');">Roll Your Own IRC Bot</a><br/><br />
<a href="http://blog.sigfpe.com/2006/05/grok-haskell-monad-transformers.html?showComment=1206303360000" onclick="javascript:pageTracker._trackPageview('/outbound/article/blog.sigfpe.com');">Grok Haskell Monad Transformers</a><br/><br />
<a href="http://www.engr.mun.ca/~theo/Misc/haskell_and_monads.htm" onclick="javascript:pageTracker._trackPageview('/outbound/article/www.engr.mun.ca');">Monads For The Working Haskell Programmer</a><br/><br />
<a href="http://www.falvotech.com/content/publications/monads/" onclick="javascript:pageTracker._trackPageview('/outbound/article/www.falvotech.com');">Haskell Monads: Another View</a><br/>
</div>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/state-monads-in-haskell/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
		<item>
		<title>Recovering A Trashed Ext3 System</title>
		<link>http://www.brool.com/index.php/recovering-a-trashed-ext3-system</link>
		<comments>http://www.brool.com/index.php/recovering-a-trashed-ext3-system#comments</comments>
		<pubDate>Tue, 10 Feb 2009 07:56:16 +0000</pubDate>
		<dc:creator>tim</dc:creator>
				<category><![CDATA[coding]]></category>
		<category><![CDATA[ext3]]></category>
		<category><![CDATA[recovery]]></category>

		<guid isPermaLink="false">http://www.brool.com/?p=149</guid>
		<description><![CDATA[My 500GB backup drive started making horrible, horrible noises when spinning up, akin to a lawnmower trying to mow a rock, so I decided that it was time get another backup drive so that I would be safe.  I picked up another drive at Fry&#8217;s (not a Maxtor this time, thank you very much; [...]]]></description>
			<content:encoded><![CDATA[<p>My 500GB backup drive started making horrible, horrible noises when spinning up, akin to a lawnmower trying to mow a rock, so I decided that it was time get another backup drive so that I would be safe.  I picked up another drive at Fry&#8217;s (not a Maxtor this time, thank you very much;  I haven&#8217;t had much luck with Maxtor) and hooked them both up to my computer so that I could completely copy from the old drive to the new drive.</p>
<p>The old drive was in /dev/sdb1, while the new drive was in /dev/sdc1, so it was the work of a few moments to type:</p>
<div class="codesnip-container" >dd if=/dev/sdc1 of=/dev/sdb1</div>
<p>See what I did there?  Yup, I <i>copied the new drive onto the old drive</i>, and, yes, I sometimes do incredibly stupid things.  I stopped it just a couple of seconds later, but I had lost the first 100MB of my drive.  </p>
<p>Most of my stuff is backed up to at least two places, but there was probably about 200GB of stuff that I had lost, non-critical non-financial files that I would have preferred to get back.  I eventually got it all back in the hackiest way possible.</p>
<p>How did I get it back?</p>
<p>1. Ran mke2fs -n to find some good superblocks.</p>
<div class="codesnip-container" >
<pre>
$ mke2fs -n /dev/sdc1
Filesystem label=
OS type: Linux
Block size=4096 (log=2)
Fragment size=4096 (log=2)
30515200 inodes, 122035756 blocks
6101787 blocks (5.00%) reserved for the super user
First data block=0
Maximum filesystem blocks=0
3725 block groups
32768 blocks per group, 32768 fragments per group
8192 inodes per group
Superblock backups stored on blocks:
	32768, 98304, 163840, 229376, 294912, 819200, 884736, 1605632, 2654208,
	4096000, 7962624, 11239424, 20480000, 23887872, 71663616, 78675968,
	102400000
</pre>
</div>
<p>2. Verified that the superblocks were good.<br />
All of the &#8220;good&#8221; superblocks should be identical.</p>
<div class="codesnip-container" >
<pre>
dd if=/dev/sdc1 skip=32768 count=1 bs=4096 | hex | head
1+0 records in
1+0 records out
4096 bytes (4.1 kB) copied, 0.00194333 s, 2.1 MB/s
0x00000000: 00 40 a3 03 2c 1e 46 07 - 05 9f 12 00 d5 c4 28 07 .@..,.F.....(.
0x00000010: f5 3f a3 03 00 00 00 00 - 02 00 00 00 02 00 00 00 .?..............
0x00000020: 00 80 00 00 00 80 00 00 - 00 40 00 00 00 00 00 00 .........@......
0x00000030: 4c db 85 47 00 00 15 00 - 53 ef 00 00 01 00 00 00 L..G....S.......
0x00000040: c2 6f 0d 3a 00 4e ed 00 - 00 00 00 00 01 00 00 00 .o.:.N..........
0x00000050: 00 00 00 00 0b 00 00 00 - 80 00 01 00 04 00 00 00 ................
0x00000060: 02 00 00 00 01 00 00 00 - e6 9f 75 ff 9c 5d 49 0a ..........u..]I.
0x00000070: 95 cb a2 fb e0 39 ce 9c - 00 00 00 00 00 00 00 00 .?9..........
0x00000080: 00 00 00 00 00 00 00 00 - 00 00 00 00 00 00 00 00 ................
0x00000090: 00 00 00 00 00 00 00 00 - 00 00 00 00 00 00 00 00 ................
</pre>
</div>
<p>I compared it with one of the later superblocks.  I was lucky and had only lost the last one. </p>
<p>2. Get a temporary root directory onto the drive.  For my particular case, I copied the start of an identically sized drive to the damaged drive so that I could get enough of a file system to work with.  </p>
<div class="codesnip-container" >dd if=/dev/sdd1 of=/dev/sdc1 count=2000 bs=4096</div>
<p>3. Scan the drive and figure out what directories you want to try to get back.  I ended up writing <a href="http://github.com/brool/util/tree/master" onclick="javascript:pageTracker._trackPageview('/outbound/article/github.com');">a small Python program</a> to scan the drive directly, finding the subdirectories that I wanted.</p>
<pre class="brush: python">
import struct
import sys

dsk = file(sys.argv[1], &quot;rb&quot;)
blocksize = 4096
block = 0

# see if this block could potentially be a directory
def isvalid(bytes):
    if len(bytes) &lt; 8:
        print &quot;error in block&quot;, block

    (inode, reclen, namelen, ftype) = struct.unpack(&quot;IHBB&quot;, bytes[0:8])

    if namelen != 1 or ftype != 2 or bytes[8] != &#039;.&#039;:
        return False

    (inode, newreclen, namelen, ftype) = struct.unpack(&quot;IHBB&quot;, bytes[reclen:reclen+8])

    if namelen != 2 or ftype != 2 or bytes[reclen+8] != &#039;.&#039; or bytes[reclen+9] != &#039;.&#039;:
        return False

    return True

# list some names in the given directory block
def names(bytes):
    ix = 0
    while ix &lt; len(bytes):
        (inode, reclen, namelen, ftype) = struct.unpack(&quot;IHBB&quot;, bytes[ix:ix+8])
        name = bytes[ix+8:ix+8+namelen]
        yield name
        ix += reclen

while True:
    bytes = dsk.read(blocksize)

    if len(bytes) == 0: break

    if isvalid(bytes):
        print &quot;block #&quot;, block
        print list(names(bytes))

    block += 1
</pre>
<p>You&#8217;re looking for directories that are as high level as possible &#8212; in my case, I had a directory to_archive that contained all the things that I hadn&#8217;t redundantly backed up.  It was at block 22839809. </p>
<p>4. Given a block number, it&#8217;s possible to convert it into an inode&#8230; but it&#8217;s much easier to just go to the directory in question and take a look at the inode for it.   </p>
<div class="codesnip-container" >dd if=/dev/sdc1 skip=22839810 count=1 bs=4096 | hex | head -n 1</div>
<p>The first four bytes are the inode.   Copy them down.</p>
<p>5. I found the temporary root directory that I copied from the other drive.</p>
<div class="codesnip-container" >python scan_directory.py /dev/sdc1<br />
block # 1539<br />
['.', '..', 'lost+found', 'var', 'etc', 'media', 'cdrom', 'bin', 'boot', 'dev', 'home', 'lib', 'mnt', 'opt', 'proc', 'root', 'sbin', 'srv', 'sys', 'tmp', 'usr', 'initrd.img', 'vmlinuz', 'initrd.img.old', 'vmlinuz.old']</div>
<p>This directory is mostly pointing into garbage, but we just want to point one directory to our stuff.</p>
<p>6. Now we want to point the inode of a directory to the one that contains our files.</p>
<div class="codesnip-container" >dd if=/dev/sdc1 of=root_directory.bin count=1 bs=4096 skip=1539</div>
<p>The root directory looks something like this.</p>
<div class="codesnip-container" >
<pre>
0x00000000: 02 00 00 00 0c 00 01 02 - 2e 00 00 00 02 00 00 00 ................
0x00000010: 0c 00 02 02 2e 2e 00 00 - 0b 00 00 00 14 00 0a 02 ................
0x00000020: 6c 6f 73 74 2b 66 6f 75 - 6e 64 00 00 01 e0 0a 00 lost+found......
0x00000030: 0c 00 03 02 76 61 72 00 - 01 40 17 00 0c 00 03 02 ....var..@......
0x00000040: 65 74 63 00 01 e0 0c 00 - 10 00 05 02 6d 65 64 69 etc.........medi
0x00000050: 61 00 00 00 0c 00 00 00 - 10 00 05 07 63 64 72 6f a...........cdro
0x00000060: 6d 00 00 00 01 00 12 00 - 0c 00 03 02 62 69 6e 00 m...........bin.
0x00000070: 01 60 20 00 0c 00 04 02 - 62 6f 6f 74 01 40 13 00 .` .....boot.@..
0x00000080: 0c 00 03 02 64 65 76 00 - 01 20 1b 00 0c 00 04 02 ....dev.. ......
0x00000090: 68 6f 6d 65 01 40 03 00 - 0c 00 03 02 6c 69 62 00 home.@......lib.
</pre>
</div>
<p>The name of a file is preceded by a a) one byte type, b) a one byte name length, c) two bytes of record length, and d) four bytes of an inode.  In this case, we&#8217;re going to change lost+found from inode 0&#215;0b to the one that we got in step 4.  Easiest way is to use dd and tweak:</p>
<div class="codesnip-container" >tweak root_directory.bin<br />
&#8230; edit it &#8230;<br />
dd if=root_directory.bin of=/dev/sdc1 count=1 bs=4096 seek=1539</div>
<p>7. Now, mount it and cross your fingers.</p>
<div class="codesnip-container" >mount -o ro /dev/sdc1 /mnt/external</div>
<p>In my case, I was lucky &#8212; I was able to get <i>everything</i> back in the directories that I cared about. </p>
]]></content:encoded>
			<wfw:commentRss>http://www.brool.com/index.php/recovering-a-trashed-ext3-system/feed</wfw:commentRss>
		<slash:comments>0</slash:comments>
		</item>
	</channel>
</rss>
