<?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/"
	xmlns:media="http://search.yahoo.com/mrss/"
	>

<channel>
	<title>The Blogmatic Programmer &#187; Lisp</title>
	<atom:link href="http://anthonyf.wordpress.com/category/lisp/feed/" rel="self" type="application/rss+xml" />
	<link>http://anthonyf.wordpress.com</link>
	<description>Just another Wordpress.com weblog</description>
	<lastBuildDate>Tue, 08 Jan 2008 02:55:43 +0000</lastBuildDate>
	<generator>http://wordpress.com/</generator>
	<language>en</language>
	<sy:updatePeriod>hourly</sy:updatePeriod>
	<sy:updateFrequency>1</sy:updateFrequency>
	<cloud domain='anthonyf.wordpress.com' port='80' path='/?rsscloud=notify' registerProcedure='' protocol='http-post' />
<image>
		<url>http://www.gravatar.com/blavatar/2b852c56f6fca8a3f0431ad67b55957b?s=96&#038;d=http://s.wordpress.com/i/buttonw-com.png</url>
		<title>The Blogmatic Programmer &#187; Lisp</title>
		<link>http://anthonyf.wordpress.com</link>
	</image>
			<item>
		<title>Lazy Streams</title>
		<link>http://anthonyf.wordpress.com/2008/01/08/lazy-streams/</link>
		<comments>http://anthonyf.wordpress.com/2008/01/08/lazy-streams/#comments</comments>
		<pubDate>Tue, 08 Jan 2008 02:55:43 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Lisp]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://anthonyf.wordpress.com/2008/01/08/lazy-streams/</guid>
		<description><![CDATA[I&#8217;ve been watching the SICP Lectures with a group of coworkers and friends.  We just finished the lectures 6a and 6b which describe how to implement lazy lists or streams.  I found these stream lectures to be very enlightening, mostly because they teach a new method of solving problems that is not typical [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=32&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>I&#8217;ve been watching the <a href="http://swiss.csail.mit.edu/classes/6.001/abelson-sussman-lectures/">SICP Lectures</a> with a group of coworkers and friends.  We just finished the lectures 6a and 6b which describe how to implement lazy lists or streams.  I found these stream lectures to be very enlightening, mostly because they teach a new method of solving problems that is not typical in your average programming job.  If you have never watched the lectures I highly recommend it!</p>
<p>Implementing streams requires two new special forms, DELAY and<br />
CONS-STREAM.  Neither the book or the video lectures go into great<br />
detail about the actual implementation of DELAY and CONS-STREAM.  I<br />
assume the reason is you need access to the compiler code or macros to<br />
implement them, and that is surely beyond the scope of the class.</p>
<p>So I decided to take a crack at implementing the code in Common Lisp,<br />
and I was surprised how simple it is.  Common lisp of course has<br />
macros, so implementing the special forms is easy:</p>
<pre style="color:#000000;background-color:#ffffff;font-size:8pt;border-style:solid;border-width:1px;padding:5px;">
(<span style="color:#a020f0;">eval-when</span> (<span style="color:#da70d6;">:compile-toplevel</span> <span style="color:#da70d6;">:load-toplevel</span> <span style="color:#da70d6;">:execute</span>)
  (<span style="color:#a020f0;">defmacro</span> <span style="color:#0000ff;">delay</span> (exp)
    <span style="color:#bc8f8f;">"creates a promise to calculate exp"</span>
    `(memo-proc #'(<span style="color:#a020f0;">lambda</span> () ,exp)))

  (<span style="color:#a020f0;">defmacro</span> <span style="color:#0000ff;">cons-stream</span> (a b)
    `(cons ,a (delay ,b))))</pre>
<p>DELAY is simply a macro that wraps its arguments into a lambda<br />
expression. This causes the evaluation of the expression to be delayed<br />
until the lambda expression is executed, using FORCE.  MEMO-PROC<br />
creates a memoized version of the lambda, making multiple calls to the<br />
expression more efficient.</p>
<p>CONS-STREAM must also be a macro because it needs to pass its<br />
second argument unevaluated to DELAY. The rest of the stream code can<br />
be implemented using plain-old-procedures.</p>
<p>You can do some pretty neat things with streams, like create a<br />
lazy Sieve of Eratosthenes:</p>
<pre style="color:#000000;background-color:#ffffff;font-size:8pt;border-style:solid;border-width:1px;padding:5px;">
(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">sieve</span> (stream)
  <span style="color:#bc8f8f;">"lazy sieve of eratosthenes"</span>
  (cons-stream
   (stream-car stream)
   (sieve (stream-filter
           #'(<span style="color:#a020f0;">lambda</span> (x)
               (not (= 0 (mod x (stream-car stream)))))
           (stream-cdr stream)))))</pre>
<pre style="color:#000000;background-color:#ffffff;font-size:8pt;border-style:solid;border-width:1px;padding:5px;">
<span style="color:#a020f0;">SICP-STREAMS&gt; </span><span style="font-weight:bold;">(defparameter primes (sieve (integers-from 2)))</span>
<span style="color:#ff0000;">PRIMES</span>
<span style="color:#a020f0;">SICP-STREAMS&gt; </span><span style="font-weight:bold;">(stream-ref primes 100)</span>
<span style="color:#ff0000;">547</span>
<span style="color:#a020f0;">SICP-STREAMS&gt; </span><span style="font-weight:bold;">(stream-ref primes 1000)</span>
<span style="color:#ff0000;">7927</span></pre>
<p>STREAM-REF finds the Nth element in the stream, so the examples<br />
show the 100th and 1000th primes.  It turns out that the lazy sieve is<br />
horribly inefficient because it creates a new stream filter for every<br />
prime found.  Finding the 10,000th prime will create 10,000 filter<br />
procedures and execute them all to find the next prime!</p>
<p>Here&#8217;s an infinite Fibonacci stream:</p>
<pre style="color:#000000;background-color:#ffffff;font-size:8pt;border-style:solid;border-width:1px;padding:5px;">
<span style="color:#a020f0;">SICP-STREAMS&gt; </span><span style="font-weight:bold;">(defparameter fibs (cons-stream
                                  0
                                  (cons-stream
                                   1
                                   (add-streams (stream-cdr fibs)
                                                fibs))))</span>
<span style="color:#ff0000;">FIBS</span>
<span style="color:#a020f0;">SICP-STREAMS&gt; </span><span style="font-weight:bold;">(stream-ref fibs 10)</span>
<span style="color:#ff0000;">55</span>
<span style="color:#a020f0;">SICP-STREAMS&gt; </span><span style="font-weight:bold;">(stream-ref fibs 50)</span>
<span style="color:#ff0000;">12586269025</span>
<span style="color:#a020f0;">SICP-STREAMS&gt; </span><span style="font-weight:bold;">(stream-ref fibs 100)</span>
<span style="color:#ff0000;">354224848179261915075</span></pre>
<p>And finally, the complete source code:</p>
<pre style="color:#000000;background-color:#ffffff;font-size:8pt;border-style:solid;border-width:1px;padding:5px;">
<span style="color:#b22222;">#|

Lazy Streams in Common Lisp
Author: Anthony Fairchild

Created: 2008.01.05
Last Modified: 2008.01.07

An implementation of the lazy streams found in SICP, using Common
Lisp.

|#</span>

(<span style="color:#a020f0;">defpackage</span> <span style="color:#228b22;">sicp-streams</span>
  (<span style="color:#da70d6;">:use</span> <span style="color:#da70d6;">:common-lisp</span>))

(<span style="color:#a020f0;">in-package</span> <span style="color:#da70d6;">:sicp-streams</span>)

<span style="color:#b22222;">;; </span><span style="color:#b22222;">(declaim (optimize (debug 3)))
</span>
(<span style="color:#a020f0;">eval-when</span> (<span style="color:#da70d6;">:compile-toplevel</span> <span style="color:#da70d6;">:load-toplevel</span> <span style="color:#da70d6;">:execute</span>)
  (<span style="color:#a020f0;">defmacro</span> <span style="color:#0000ff;">delay</span> (exp)
    <span style="color:#bc8f8f;">"creates a promise to calculate exp"</span>
    `(memo-proc #'(<span style="color:#a020f0;">lambda</span> () ,exp)))

  (<span style="color:#a020f0;">defmacro</span> <span style="color:#0000ff;">cons-stream</span> (a b)
    `(cons ,a (delay ,b))))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">memo-proc</span> (proc)
    <span style="color:#bc8f8f;">"returns a memoized version of proc"</span>
    (<span style="color:#a020f0;">let</span> ((already-run-p nil)
          (result nil))
      #'(<span style="color:#a020f0;">lambda</span> ()
          (<span style="color:#a020f0;">if</span> already-run-p
              result
              (<span style="color:#a020f0;">progn</span> (setf result (funcall proc))
                     (setf already-run-p t)
                     result)))))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">force</span> (exp)
    <span style="color:#bc8f8f;">"evaluates a previously created promise"</span>
    (funcall exp))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">stream-car</span> (s) (car s))
(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">stream-cdr</span> (s) (force (cdr s)))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">stream-ref</span> (s n)
  <span style="color:#bc8f8f;">"finds the Nth element of stream S"</span>
  (<span style="color:#a020f0;">if</span> (= 0 n)
      (stream-car s)
      (stream-ref (stream-cdr s) (- n 1))))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">stream-map</span> (proc <span style="color:#228b22;">&amp;rest</span> streams)
  <span style="color:#bc8f8f;">"executes PROC for every element in each stream"</span>
  (<span style="color:#a020f0;">if</span> (null streams)
      nil
      (cons-stream
       (apply proc (mapcar #'stream-car streams))
       (apply #'stream-map
              proc
              (mapcar #'stream-cdr streams)))))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">stream-filter</span> (pred stream)
  (<span style="color:#a020f0;">cond</span> ((not stream) nil)
        ((funcall pred (stream-car stream))
         (cons-stream (stream-car stream)
                      (stream-filter pred
                                     (stream-cdr stream))))
        (t (stream-filter pred (stream-cdr stream)))))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">add-streams</span> (s1 s2)
  (stream-map #'+ s1 s2))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">stream-for-each</span> (proc stream)
  (<span style="color:#a020f0;">if</span> (not stream)
      'done
      (<span style="color:#a020f0;">progn</span> (funcall proc (stream-car stream))
             (stream-for-each proc (stream-cdr stream)))))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">print-stream</span> (stream)
  (stream-for-each #'print stream))

<span style="color:#b22222;">;;;; </span><span style="color:#b22222;">Example Usage ;;;;
</span>
(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">integers-from</span> (n)`
  <span style="color:#bc8f8f;">"returns a stream of integers starting from N"</span>
  (cons-stream n (integers-from (+ n 1))))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">sieve</span> (stream)
  <span style="color:#bc8f8f;">"lazy sieve of eratosthenes"</span>
  (cons-stream
   (stream-car stream)
   (sieve (stream-filter
           #'(<span style="color:#a020f0;">lambda</span> (x)
               (not (= 0 (mod x (stream-car stream)))))
           (stream-cdr stream)))))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">make-primes-stream</span> ()
  (sieve (integers-from 2)))

(<span style="color:#a020f0;">defun</span> <span style="color:#0000ff;">make-fibs-stream</span> ()
  (<span style="color:#a020f0;">let</span> ((fibs nil))
    (setf fibs (cons-stream
                0
                (cons-stream
                 1
                 (add-streams (stream-cdr fibs)
                              fibs))))
    fibs))</pre>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/32/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/32/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/32/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/32/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/32/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/32/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/32/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/32/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/32/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/32/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/32/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/32/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=32&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2008/01/08/lazy-streams/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>
	</item>
		<item>
		<title>Continuo: Part 2</title>
		<link>http://anthonyf.wordpress.com/2007/02/09/continuo-part-2/</link>
		<comments>http://anthonyf.wordpress.com/2007/02/09/continuo-part-2/#comments</comments>
		<pubDate>Fri, 09 Feb 2007 06:32:13 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Lisp]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://anthonyf.wordpress.com/2007/02/09/continuo-part-2/</guid>
		<description><![CDATA[I decided to create a more graphical view of my continuo game. I find it easier to look at compared to the ASCII version in my previous entry.   The color chains are much easier to follow.
I used lispbuilder-sdl to generate the graphics.  Each 4&#215;4 card has a thick black border and is [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=30&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>I decided to create a more graphical view of my continuo game. I find it easier to look at compared to the ASCII version in my previous entry.   The color chains are much easier to follow.</p>
<p>I used lispbuilder-sdl to generate the graphics.  Each 4&#215;4 card has a thick black border and is labelled with a number representing the play order.</p>
<p>Score: 908</p>
<p><a href="http://img524.imageshack.us/my.php?image=continuoscreenshot116qx7.png" target="_blank"><img src="http://img524.imageshack.us/img524/4026/continuoscreenshot116qx7.th.png" alt="Free Image Hosting at www.ImageShack.us" border="0" /></a></p>
<p>Score: 919</p>
<p><a href="http://img521.imageshack.us/my.php?image=continuoscreenshot253zz8.png" target="_blank"><img src="http://img521.imageshack.us/img521/2205/continuoscreenshot253zz8.th.png" alt="Free Image Hosting at www.ImageShack.us" border="0" /></a></p>
<p>Score: 799</p>
<p><a href="http://img63.imageshack.us/my.php?image=continuoscreenshot630xv9.png" target="_blank"><img src="http://img63.imageshack.us/img63/6295/continuoscreenshot630xv9.th.png" alt="Free Image Hosting at www.ImageShack.us" border="0" /></a></p>
<p>Score: 830</p>
<p><a href="http://img63.imageshack.us/my.php?image=continuoscreenshot758kv6.png" target="_blank"><img src="http://img63.imageshack.us/img63/8430/continuoscreenshot758kv6.th.png" alt="Free Image Hosting at www.ImageShack.us" border="0" /></a></p>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/30/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/30/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/30/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/30/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/30/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/30/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/30/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/30/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/30/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/30/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/30/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/30/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=30&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2007/02/09/continuo-part-2/feed/</wfw:commentRss>
		<slash:comments>8</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>

		<media:content url="http://img524.imageshack.us/img524/4026/continuoscreenshot116qx7.th.png" medium="image">
			<media:title type="html">Free Image Hosting at www.ImageShack.us</media:title>
		</media:content>

		<media:content url="http://img521.imageshack.us/img521/2205/continuoscreenshot253zz8.th.png" medium="image">
			<media:title type="html">Free Image Hosting at www.ImageShack.us</media:title>
		</media:content>

		<media:content url="http://img63.imageshack.us/img63/6295/continuoscreenshot630xv9.th.png" medium="image">
			<media:title type="html">Free Image Hosting at www.ImageShack.us</media:title>
		</media:content>

		<media:content url="http://img63.imageshack.us/img63/8430/continuoscreenshot758kv6.th.png" medium="image">
			<media:title type="html">Free Image Hosting at www.ImageShack.us</media:title>
		</media:content>
	</item>
		<item>
		<title>Continuo: My ILC contest entry</title>
		<link>http://anthonyf.wordpress.com/2007/02/07/continuo-my-ilc-contest-entry/</link>
		<comments>http://anthonyf.wordpress.com/2007/02/07/continuo-my-ilc-contest-entry/#comments</comments>
		<pubDate>Wed, 07 Feb 2007 07:43:05 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Lisp]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">http://anthonyf.wordpress.com/2007/02/07/continuo-my-ilc-contest-entry/</guid>
		<description><![CDATA[This year&#8217;s International Lisp Conference is having a programming contest for those attending.  Unfortunately for me, I live in the Seattle, WA area and the conference is in Cambridge, England!  I love contests like this anyway so I decided to take a crack at it.
The contest is to play a solitaire version of [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=29&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>This year&#8217;s <a href="http://www.international-lisp-conference.org/2007/index">International Lisp Conference</a> is having a programming <a href="http://www.international-lisp-conference.org/2007/contest">contest</a> for those attending.  Unfortunately for me, I live in the Seattle, WA area and the conference is in Cambridge, England!  I love contests like this anyway so I decided to take a crack at it.</p>
<p>The contest is to play a solitaire version of the card game <a href="http://www.blackdogaccessories.com/card_games_main24.htm">Continuo</a>.   The <a href="http://www.international-lisp-conference.org/2007/contest">contest</a> page gives a good description of how the game is played so I wont get into that here.  The game looks like a lot of fun so I ordered a copy of the real game from a local game shop.</p>
<p>My Lisp solution is very naive but appears to play a decent game.  It simply plays the next card in the highest scoring position.  I think higher overall scores could be achieved if you take into account cards that have been played already as well as the ones not yet played.  I cant really wrap my brain around that one at the moment so my naive solution works just fine for now <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' /> </p>
<p>I wont post my code until the contest is over, but I will say that it is about 200 lines of highly unoptimized code, including comments and some test code.  Using SBCL on Linux it runs in about 16 seconds and conses like nobody&#8217;s business.  Here&#8217;s an example run with test data that scores 852.</p>
<pre>
CONTINUO&gt; (time (play-continuo '(:RBRB :GYGB :GYRY :BYBY :RBYR :RGRB :RGBG
                                 :BYGY :RGRY :RBRY :RYRY :RYGY :YRBY :BYRY
                                 :BRBY :GBYB :RBGB :GBGB :RYBY :RYRG :GYBY
                                 :RGYR :GBRB :RBYB :YGBY :GBGY :GRBG :BRGB
                                 :YRGY :BGBY :GYGY :RYRB :GRYG :GRGY :RBRG
                                 :RGYG :BGYB :BRYB :GBYG :RGRG :GRGB :RGBR)))
score=852
    - - - - - - - - - - - - - - - - - - - -
    2 1 1 1 1 1 1 1 1 1 1                                       1 1 1 1 1 1
    0 9 8 7 6 5 4 3 2 1 0 9 8 7 6 5 4 3 2 1 0 1 2 3 4 5 6 7 8 9 0 1 2 3 4 5
-22                 G R G B
-21                 R R G G G Y B G
-20                 G G R R Y Y B B
-19                 B G R G B B Y Y
-18                 Y G R G G B Y G R G Y G
-17                 G G R R Y G Y G G G Y Y
-16                 R R G G G G Y Y Y Y G G R G R G
-15                 G R G Y Y Y G G G Y G R G G R R
-14                 B Y B R G Y G Y R Y G R R R G G
-13                 Y Y B B G Y B Y Y Y G G G R G R
-12         Y G B G B B Y Y Y Y B B G G Y Y Y R G Y     B R Y B
-11         G G B B R B Y B B B Y Y R G Y R R R G G     R R Y Y
-10 B Y G B B B G G Y B Y R Y B Y G Y G Y R G G R R     Y Y R R
 -9 Y Y G G G B G Y B B Y Y Y R Y B G G Y Y Y G R Y     B Y R B
 -8 G G Y Y Y B G Y Y Y B B R R Y Y Y Y G G R Y R Y B R B G R B R G
 -7 B G Y B B B G G R Y B Y Y Y R R R Y G Y Y Y R R R R B B B B R R
 -6 G R Y G G G B B B Y B G B Y R Y B Y G Y R R Y Y B B R R R R B B
 -5 R R Y Y Y G B Y Y Y B B B Y B Y Y Y G G Y R Y R G B R B G R B R R G B R
 -4 Y Y R R B G B Y B B Y Y Y Y B B G G Y Y Y R B R Y B R Y G R B G G G B B
 -3 G Y R G G G B B G B Y B B B Y Y Y G Y B R R B B B B R R R R B B B B G G
 -2         B B G G G R Y R Y B Y B B G Y G B B R R R R B B B B R R R B G R
 -1         Y B G B R R Y Y Y R Y G G G Y Y R B R Y Y R B Y G B R G
  0                 Y Y R R R R Y Y Y Y G G R B R B B R B Y   B R G B
  1                 R Y R G Y Y R R G Y G B B B R R R R B B   R R G G
  2                 R Y R B G Y R Y R Y B R R R B B B B R R   G G R R
  3                 Y Y R R R G R Y Y Y B B B R B R Y B R B   B G R B
  4                 R R Y Y G G R R B B Y Y B R G R R B G B
  5                 B R Y R R R G G R B Y R R R G G B B G G
  6                         Y R G R G B G R G G R R G G B B
  7                         G B G B B B G G R G R B B G B R
  8                         B B G G G G B B
  9                         G G B B R G B G
 10                         B G B G
Evaluation took:
  16.28 seconds of real time
  15.820989 seconds of user run time
  0.220014 seconds of system run time
  [Run times include 1.612 seconds GC run time.]
  0 page faults and
  1,848,458,504 bytes consed.
NIL</pre>
<p><strong>EDIT:</strong> I used slime-profile-package to profile my code and was able to make a very small change that produces the same result as above in only 1.35 seconds.  I really love slime <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' /> </p>
<pre>
Evaluation took:
  1.35 seconds of real time
  1.352084 seconds of user run time
  0.0 seconds of system run time
  [Run times include 0.048 seconds GC run time.]
  0 page faults and
  62,727,048 bytes consed.</pre>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/29/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/29/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/29/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/29/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/29/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/29/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/29/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/29/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/29/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/29/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/29/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/29/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=29&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2007/02/07/continuo-my-ilc-contest-entry/feed/</wfw:commentRss>
		<slash:comments>0</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>
	</item>
		<item>
		<title>A Lispy Jigsaw Puzzle Game</title>
		<link>http://anthonyf.wordpress.com/2006/12/27/a-lispy-jigsaw-puzzle-game/</link>
		<comments>http://anthonyf.wordpress.com/2006/12/27/a-lispy-jigsaw-puzzle-game/#comments</comments>
		<pubDate>Wed, 27 Dec 2006 05:18:17 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Lisp]]></category>

		<guid isPermaLink="false">http://anthonyf.wordpress.com/2006/12/27/a-lispy-jigsaw-puzzle-game/</guid>
		<description><![CDATA[My blog has been neglected lately, but I have a good reason.   I&#8217;ve been playing around with lispbuilder-sdl, a Lisp interface to SDL, used for creating games.  I decided to resurrect an old jigsaw puzzle game I wrote a few years ago using pygame.  The game was never really finished, as [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=27&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>My blog has been neglected lately, but I have a good reason.   I&#8217;ve been playing around with <a href="http://lispbuilder.sourceforge.net/">lispbuilder-sdl</a>, a Lisp interface to <a href="http://www.libsdl.org">SDL</a>, used for creating games.  I decided to resurrect an old jigsaw puzzle game I wrote a few years ago using <a href="http://www.pygame.org">pygame</a>.  The game was never really finished, as with many of my other personal programming projects.</p>
<p>Converting the old Python code to Lisp was fun.  I was able to simplify a lot and performance is much better, mostly due to Lisp being a compiled language.  The python version was slow and I really had no way to optimize unless I wrote C extensions.  Now with Lisp I can profile the code and add compiler optimizations and declarations to speed things up where they need to be.  I still have the option to write C extensions but its unlikely I&#8217;ll need to for this game.</p>
<p>Creating each jigsaw puzzle piece was a little challenging and very processor intensive.  I start by chopping up an image into square pieces.  Each piece overlaps adjacent pieces by about 1/3.  These pieces are then rotated 90, 180 and 270 degrees.   Next I create a mask image where I draw the puzzle piece outline using bézier curves.  I flood fill the outside of the mask image with the mask color, then blit it onto original piece image.   Repeat for each rotation.  OK, I think I left a few steps out, but my point is, it takes a while to create a puzzle from a source image.  Using this process I can create a puzzle from any image.</p>
<p>Each puzzle piece is placed randomly on the screen.  Right clicking a piece rotates it.  Pieces that belong together can be joined by dragging one piece next to another.  They snap together and then remain joined when moving them around.  Joined pieces can also be rotated.</p>
<p>It is nowhere near done.    I plan on adding many features, at least enough to be able to call it a beta.  I would like to get a website with a downloadable binary and source code going soon.  Hopefully I can maintain my interest in this and finish something for a change <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_wink.gif' alt=';-)' class='wp-smiley' /> </p>
<p>Here are few screenshots of the game (sorry about the imageshack ads):</p>
<table>
<tr>
<td><a href="http://img245.imageshack.us/my.php?image=screenshotdq2.jpg" target="_blank"><img src="http://img245.imageshack.us/img245/467/screenshotdq2.th.jpg" border="0" /></a></td>
<td><a href="http://img187.imageshack.us/my.php?image=screenshot2bl1.jpg" target="_blank"><img src="http://img187.imageshack.us/img187/1249/screenshot2bl1.th.jpg" border="0" /></a></td>
</tr>
<tr>
<td><a href="http://img187.imageshack.us/my.php?image=screenshot3xt0.jpg" target="_blank"><img src="http://img187.imageshack.us/img187/3163/screenshot3xt0.th.jpg" border="0" /></a></td>
<td><a href="http://img187.imageshack.us/my.php?image=screenshot4tp1.jpg" target="_blank"><img src="http://img187.imageshack.us/img187/7636/screenshot4tp1.th.jpg" border="0" /></a></td>
</tr>
</table>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/27/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/27/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/27/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/27/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/27/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/27/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/27/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/27/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/27/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/27/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/27/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/27/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=27&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2006/12/27/a-lispy-jigsaw-puzzle-game/feed/</wfw:commentRss>
		<slash:comments>11</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>

		<media:content url="http://img245.imageshack.us/img245/467/screenshotdq2.th.jpg" medium="image" />

		<media:content url="http://img187.imageshack.us/img187/1249/screenshot2bl1.th.jpg" medium="image" />

		<media:content url="http://img187.imageshack.us/img187/3163/screenshot3xt0.th.jpg" medium="image" />

		<media:content url="http://img187.imageshack.us/img187/7636/screenshot4tp1.th.jpg" medium="image" />
	</item>
		<item>
		<title>Coding in !C (or using fseek to make really huge files quickly)</title>
		<link>http://anthonyf.wordpress.com/2006/08/30/coding-in-c/</link>
		<comments>http://anthonyf.wordpress.com/2006/08/30/coding-in-c/#comments</comments>
		<pubDate>Wed, 30 Aug 2006 01:03:39 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Lisp]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">https://anthonyf.wordpress.com/2006/08/30/coding-in-c/</guid>
		<description><![CDATA[I&#8217;ve been crazy busy at work so I&#8217;ve been slacking on my posts.  Lots of cool things to write about but not enough time!  On a positive note I&#8217;ve been doing more utility code in Lisp at work.  At work I call Lisp !C (not C) to avoid any political issues that [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=23&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>I&#8217;ve been crazy busy at work so I&#8217;ve been slacking on my posts.  Lots of cool things to write about but not enough time!  On a positive note I&#8217;ve been doing more utility code in Lisp at work.  At work I call Lisp !C (not C) to avoid any political issues that could arise.  When asked &#8220;What&#8217;s !C?&#8221;,  I answer &#8220;Its like C, only better!  It&#8217;s all the rage!  Everyone is doing it!&#8221;.</p>
<p>This past weekend I worked on a program for work that fragments the hell out of a hard disk.  Why, you ask?  Its a tool to test the performance of our product under extreme conditions.  It fragments the disk by creating files of random size util it reaches a free space threshold, then deletes random files which it previously created.  After a few deletes, it creates more randomly sized files.  Rinse, repeat.  If you let the program run for a while on a disk it produces files with 200+ fragments.</p>
<p>The first working version of the code was horribly slow. It took an *extremely* long time to fill up a disk with files before it got to the delete stage.  The file writes were taking way to long to complete.  I got to talking to my coworker about this problem and he suggested an old hack which I have never heard of.  Instead of writing data to the files, use fseek() to seek to the position where the desired EOF should be and then write a single byte to it.   This technique can be used to create huge files in a matter of milliseconds.  He explained that this hack can be used to &#8220;see&#8221; the data in the free space on a disk.  How evil is that?</p>
<p>Changing my code to use the new technique made it orders of magnitude faster.  But it wasn&#8217;t long before we discovered a bug in the new system.  I was able to allocate huge files on the system (1GB+) but it would not decrease the amount of free space on the disk.  After a throwing out a few wild a crazy theories about it my coworker and I finally discovered what was going on.  The file system was not reserving space for blocks that were not written to.  So for a 1GB file only one block was getting reserved.  The rest of the file must be in the &#8220;free block pool&#8221; until data is written to it.</p>
<p>To fix the problem I changed the code to write out a single byte per block, thus allocating the the entire block without the overhead of filling the entire block with data.  This solution is not quite as fast but it is still way more efficient than the original one, and it works!</p>
<p>The program was written in CLISP, which is a very cool Lisp for doing shell scripting an quick one-off utilities. Here&#8217;s the code for the function that eats the disk space:</p>
<pre>(<font color="#a020f0">defun</font> <font color="#0000ff">eat-space</font> (file-name size)
  <font color="#bc8f8f">"Create a bogus file that chews up disk space.  Size is in bytes."</font>
  (<font color="#a020f0">let</font> ((file (linux:fopen file-name <font color="#bc8f8f">"w"</font>)))
    <font color="#b22222">;; write a byte every 4k so a block gets allocated
</font>    (<font color="#a020f0">loop</font> for x from 0 to (1- size) by 4096
          do (<font color="#a020f0">progn</font> (linux:fseek file x 0)
                    (linux:fputc 1 file)))
    (linux:fclose file)))</pre>
<p>One other thing to note for any lispers that may be reading this.  The code above uses the LINUX package in CLISP, not the standard CL file IO functions.  The reason I cannot use the standard functions is FILE-POSITION throws an error when attempting the seek past the end of a file.  So in other words, the seek hack does not work in standard common lisp (or at least CLISP&#8217;s version of it).</p>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/23/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/23/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/23/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/23/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/23/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/23/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/23/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/23/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/23/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/23/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/23/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/23/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=23&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2006/08/30/coding-in-c/feed/</wfw:commentRss>
		<slash:comments>8</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>
	</item>
		<item>
		<title>Reader Macros</title>
		<link>http://anthonyf.wordpress.com/2006/08/08/reader-macros/</link>
		<comments>http://anthonyf.wordpress.com/2006/08/08/reader-macros/#comments</comments>
		<pubDate>Tue, 08 Aug 2006 23:27:46 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Lisp]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">https://anthonyf.wordpress.com/2006/08/08/reader-macros/</guid>
		<description><![CDATA[I&#8217;m working on a Lisp program for a friend right now that will import old blog entries from a giant XML file.  The file is about 60MB, mostly containing images in base64 format.  I&#8217;m using CL-XMLS to parse the XML file and for some reason it takes a *long* time (15+ minutes) to [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=22&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>I&#8217;m working on a Lisp program for a friend right now that will import old blog entries from a giant XML file.  The file is about 60MB, mostly containing images in base64 format.  I&#8217;m using CL-XMLS to parse the XML file and for some reason it takes a *long* time (15+ minutes) to parse a large file.  It could be that the library was never meant to parse files that big.  So working with this data file is a real pain.</p>
<p><b>Disclaimer:</b> I&#8217;m going to have to say at this point that I&#8217;ve only been coding Lisp for a year, maybe a little more, so I may get some of this wrong.  Corrections are welcome!</p>
<p><b><span>Edit:</span></b> See Levi&#8217;s comments and corrections below as I am a bit mixed up on terminology.</p>
<p>Common Lisp has a handy feature that makes working with large amounts of external data easier:  reader macros.   A reader macro allows you to embed the results of a lisp expression into your code.  The lisp expression can be anything, like loading an image file or in my case, a very large XML file.  This pushes the time it takes to load the XML file to compile time, rather than run time.  Once I&#8217;ve compiled the source file, everything is fast binary data at that point.  As long as the XML data or the source file doesn&#8217;t change, I never have to load it again.</p>
<p>Here are the details.  I have a file called blog.lisp that contains the code to load the data from the XML file and the reader macro to embed the results into the code:</p>
<pre>(<font color="#a020f0">in-package</font> <font color="#da70d6">:erik-blog</font>)

(<font color="#a020f0">eval-when</font> (<font color="#da70d6">:compile-toplevel</font> <font color="#da70d6">:load-toplevel</font> <font color="#da70d6">:execute</font>)
  (<font color="#a020f0">defun</font> <font color="#0000ff">parse-blog</font> ()
    (<font color="#a020f0">with-open-file</font> (in (merge-pathnames #p<font color="#bc8f8f">"erik-blog.xml"</font> (util:source-file-directory)))
      (xmls:parse in))))

(<font color="#a020f0">defvar</font> <font color="#b8860b">*blog-data*</font> '#.(parse-blog))</pre>
<p>In Common Lisp the syntax for a reader macro is #.(some lisp expression).  The last line above embeds the results of the PARSE-BLOG function into the code, which then gets assigned to *BLOG-DATA*.  When blog.lisp is compiled, it produces a blog.fasl file which is like a .obj file in C except it can be dynamically loaded.  The blog.fasl file that is produced is large because it contains the entire binary representation of the blog data.  It takes about a second to load the FASL file into my running lisp image but that is nothing compared to the 15+ minutes it would take to load it from scratch.</p>
<p>This technique can be used to embed any type of data asset into an application.  I read somewhere on-line about a game company (Naughty Dog) that compiled graphics, sounds and other assets into their Lisp game.   Very cool stuff!</p>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/22/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/22/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/22/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/22/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/22/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/22/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/22/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/22/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/22/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/22/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/22/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/22/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=22&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2006/08/08/reader-macros/feed/</wfw:commentRss>
		<slash:comments>5</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>
	</item>
		<item>
		<title>Finally using Lisp at work</title>
		<link>http://anthonyf.wordpress.com/2006/07/26/finally-using-lisp-at-work/</link>
		<comments>http://anthonyf.wordpress.com/2006/07/26/finally-using-lisp-at-work/#comments</comments>
		<pubDate>Wed, 26 Jul 2006 00:33:32 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Lisp]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">https://anthonyf.wordpress.com/2006/07/26/finally-using-lisp-at-work/</guid>
		<description><![CDATA[I wrote my first Lisp program for work today.   Its a short program that traverses a huge file system (about 1 TB) and finds duplicate files and then prints a nice report showing file names, counts, space consumed, etc.   Ok, it does a little more than that but I can&#8217;t talk about the specifics [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=20&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>I wrote my first Lisp program for work today.   Its a short program that traverses a huge file system (about 1 TB) and finds duplicate files and then prints a nice report showing file names, counts, space consumed, etc.   Ok, it does a little more than that but I can&#8217;t talk about the specifics <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_wink.gif' alt=';-)' class='wp-smiley' /> .    Anyway, I had a lot of fun writing it and I finally got a good grasp of working with pathnames, which can be a little confusing in Lisp.  I also got to use quite a bit of my existing utility code like my <a href="http://anthonyf.wordpress.com/2006/06/21/pretty-printing-tables/">table printer</a>.</p>
<p>I hope to be able to write more Lisp code at work.  Its unlikely that I will be able to do anything big with it but the quick one-offs are very easy to sneak in without too much resistance!</p>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/20/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/20/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/20/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/20/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/20/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/20/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/20/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/20/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/20/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/20/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/20/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/20/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=20&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2006/07/26/finally-using-lisp-at-work/feed/</wfw:commentRss>
		<slash:comments>1</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>
	</item>
		<item>
		<title>Learn Lisp in 5 easily written steps</title>
		<link>http://anthonyf.wordpress.com/2006/07/13/learn-lisp-in-5-easlily-written-steps/</link>
		<comments>http://anthonyf.wordpress.com/2006/07/13/learn-lisp-in-5-easlily-written-steps/#comments</comments>
		<pubDate>Thu, 13 Jul 2006 19:57:56 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Emacs]]></category>
		<category><![CDATA[Lisp]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">https://anthonyf.wordpress.com/2006/07/13/learn-lisp-in-5-easlily-written-steps/</guid>
		<description><![CDATA[Learning Lisp has been a very enlightening experience for me.  But getting the development environment up and running can be quite a chore, especially for a newbie.  This can very discouraging if you are used to batteries-included programming languages like Python, Perl, Ruby and even C#.    All I can say [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=19&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>Learning Lisp has been a very enlightening experience for me.  But getting the development environment up and running can be quite a chore, especially for a newbie.  This can very discouraging if you are used to batteries-included programming languages like Python, Perl, Ruby and even C#.    All I can say is be patient, learning Lisp is good for you!</p>
<ol>
<li>Install Linux &#8211; If you already use Linux then you will likely not have much trouble with the rest of the steps.   If you don&#8217;t use Linux, why not??   It&#8217;s free!   Go download <a href="http://www.ubuntu.com/">Ubuntu Linux</a> or vanilla <a href="http://www.debian.org/">Debian</a>.   Learn to use the package manager.   I&#8217;m suggesting Linux because it supports all of the open source Common Lisp implementations.   Windows has great support for commercial implementations and very poor support (but getting better) for the open source CL&#8217;s.   I know others use MacOS but I can&#8217;t comment since I don&#8217;t own a Mac (yet!).</li>
<li>Learn <a href="http://www.gnu.org/software/emacs/">Emacs</a> &#8211; I mean *really* learn it.   Learn how to use the help system.   Learn Elisp.  Learn how to customize it but don&#8217;t try to turn Emacs into Notepad or Visual Studio or Vi(m) or whatever your old favorite editor is.  Use it the way it was meant to be used.   Steal relentlessly and unapologetically from other people&#8217;s .emacs config files.   In addition to Lisp,  Emacs supports just about every other language.  Try using it as your primary development environment.</li>
<li>Use <a href="http://common-lisp.net/project/slime/">Slime</a> &#8211; Slime stands for Superior Lisp Interaction Mode for Emacs.   It is simply the best way to develop Lisp code.  It has code completion (intellisense), context sensitive help, and includes one of the best debuggers I&#8217;ve ever worked with.</li>
<li>Read some Lisp books &#8211; <a href="http://www.gigamonkeys.com/book/">Practical Common Lisp</a> by Peter Seibel is a great starter book.   The examples are, as the book title indicates, very practical and additionally easy to follow.   Paul Graham&#8217;s <a href="http://www.paulgraham.com/acl.html">ANSI Common Lisp</a> is another good beginner&#8217;s book which includes a bonus language reference in the back.</li>
<li>After going though all of the exercises in one or two Lisp books, write a medium-large program using Lisp.   Pick something you have done before in another language, or something totally new.   The best way to learn a language is to write code!</li>
</ol>
<p>And that&#8217;s it!   Easy right?   Learning Lisp can tough but it is well worth the effort.   I&#8217;m so spoiled with it now that I go through severe withdrawals when I have to use Java or C++.</p>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/19/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/19/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/19/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/19/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/19/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/19/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/19/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/19/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/19/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/19/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/19/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/19/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=19&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2006/07/13/learn-lisp-in-5-easlily-written-steps/feed/</wfw:commentRss>
		<slash:comments>4</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>
	</item>
		<item>
		<title>Solving The Knight&#8217;s Tour</title>
		<link>http://anthonyf.wordpress.com/2006/07/07/solving-the-knights-tour/</link>
		<comments>http://anthonyf.wordpress.com/2006/07/07/solving-the-knights-tour/#comments</comments>
		<pubDate>Fri, 07 Jul 2006 01:18:31 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Lisp]]></category>
		<category><![CDATA[Programming]]></category>

		<guid isPermaLink="false">https://anthonyf.wordpress.com/2006/07/07/solving-the-knights-tour/</guid>
		<description><![CDATA[I really enjoy solving computer programming puzzles.   They are great for exercising the brain and learning new programming languages.  One of my all time favorites is The Knight&#8217;s Tour, which was given to me as an assignment in college back in &#8216;93.
The basic idea is this:  Place a knight on a [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=18&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>I really enjoy solving computer programming puzzles.   They are great for exercising the brain and learning new programming languages.  One of my all time favorites is The Knight&#8217;s Tour, which was given to me as an assignment in college back in &#8216;93.</p>
<p>The basic idea is this:  Place a knight on a standard chessboard in a random starting position.  Move the knight using normal L-shaped knight moves to every position on the board without moving to any position twice.  There is more than one solution for a given starting point.  The smallest solvable board size is 6&#215;6.  If you are solving this by hand then it is best to mark the traveled positions with a number.  For example, here&#8217;s a solved puzzle:</p>
<pre>1 |16|31|56|3 |18|21|50
--+--+--+--+--+--+--+--
30|55|2 |17|48|51|4 |19
--+--+--+--+--+--+--+--
15|32|57|54|45|20|49|22
--+--+--+--+--+--+--+--
58|29|44|47|52|63|42|5
--+--+--+--+--+--+--+--
33|14|53|64|43|46|23|40
--+--+--+--+--+--+--+--
28|59|34|37|62|41|6 |9
--+--+--+--+--+--+--+--
13|36|61|26|11|8 |39|24
--+--+--+--+--+--+--+--
60|27|12|35|38|25|10|7</pre>
<p>Back in college I wrote two solutions: a brute force solution and what I call the &#8220;look ahead&#8221; solution.   On an 8&#215;8 chessboard the brute force solution, written in C++,  took 14 days to solve on a 486 DX2.  The &#8220;look ahead&#8221; method can solve it in microseconds.   The brute force method travels to every possible position until it finds a solution while the look-ahead method chooses the best move from the next possible moves.  The best move is determined by &#8220;looking ahead&#8221; at the next 2 moves and choosing the move with the least number possible moves.  Don&#8217;t ask me why it works, it just does!</p>
<p>I&#8217;ve written Knight&#8217;s Tour solutions in just about every language I&#8217;ve learned since &#8216;93 including Java, Python, Ruby and Common Lisp.  The Common Lisp solution I wrote is by far the most elegant, not necessarily because its written in Common Lisp.  It is mostly because I&#8217;m now more experienced as a developer and at solving this particular problem <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_razz.gif' alt=':-P' class='wp-smiley' /> </p>
<p>My CL solution is 63 lines of code with comments.  If you find a bug you win a free one year subscription to my blog!</p>
<pre><font color="#b22222">#|
The Knight's Tour
Author: Anthony Fairchild
|#</font>

(<font color="#a020f0">defun</font> <font color="#0000ff">make-chessboard</font> (size-xy)
  <font color="#bc8f8f">"creates a two dimensional array representing a chessboard"</font>
  (make-array (list size-xy size-xy)))

(<font color="#a020f0">defun</font> <font color="#0000ff">is-valid-move</font> (board pos-x pos-y)
  <font color="#bc8f8f">"Returns true if the given move is valid.  A move is valid if it is
   within the board dimensions and it is not taken by another position."</font>
  (and (&lt; pos-x (array-dimension board 0))
       (&lt; pos-y (array-dimension board 1))
       (&gt;= pos-x 0)(&gt;= pos-y 0)
       (zerop (aref board pos-x pos-y))))

(<font color="#a020f0">defun</font> <font color="#0000ff">next-valid-moves</font> (board curx cury)
  <font color="#bc8f8f">"returns next 8 possible valid moves"</font>
  (<font color="#a020f0">loop</font> for pair in '((-1 2)(-2 1)(1 -2)(2 -1)(-1 -2)(-2 -1)(1 2)(2 1))
        for newx = (+ (first pair) curx)
        for newy = (+ (second pair) cury)
        when (is-valid-move board newx newy)
        collect (list newx newy)))

(<font color="#a020f0">defun</font> <font color="#0000ff">next-optimized-moves</font> (board curx cury)
  <font color="#bc8f8f">"Sorts the next valid moves with the best moves first.  The best move is
   determined by looking ahead at the next 2 moves and choosing the move
   with the least number of possible moves"</font>
  (sort (next-valid-moves board curx cury)
        #'(<font color="#a020f0">lambda</font> (move-a move-b)
            (&lt; (length (next-valid-moves board (first move-a) (second move-a)))
               (length (next-valid-moves board (first move-b) (second move-b)))))))

(<font color="#a020f0">defun</font> <font color="#0000ff">solve-knights-tour</font> (board posx posy move-num next-moves-fun)
  <font color="#bc8f8f">"Solves the knight's tour recursively. Uses next-move-fun function
to determine next move. Both brute force and optimized methods use
this function as a base."</font>
  (setf (aref board posx posy) move-num)
  (<font color="#a020f0">cond</font> ((= move-num (* (array-dimension board 0)
                        (array-dimension board 1))) board)
        ((<font color="#a020f0">loop</font> for move in (funcall next-moves-fun board posx posy)
               when (solve-knights-tour board (first move)
                                        (second move) (1+ move-num)
                                        next-moves-fun)
               return t) board)
        (t (setf (aref board posx posy) 0) nil)))

(<font color="#a020f0">defun</font> <font color="#0000ff">solve-optimized</font> (board posx posy move-num)
  <font color="#bc8f8f">"Solves the knight's tour intelligently by finding the most likely
good position to move to."</font>
  (solve-knights-tour board posx posy move-num #'next-optimized-moves))  

(<font color="#a020f0">defun</font> <font color="#0000ff">solve-brute-force</font> (board posx posy move-num)
  <font color="#bc8f8f">"Solves the knight's tour using brute force.  This means travel to every
possible position."</font>
  (solve-knights-tour board posx posy move-num #'next-valid-moves))

(<font color="#a020f0">defun</font> <font color="#0000ff">knights-tour</font> (<font color="#228b22">&amp;key</font> (optimized t)(size-xy 8)(start-x (random size-xy))(start-y (random size-xy)))
  <font color="#bc8f8f">"Return a solution for the knight's tour or nil if no solution could be found"</font>
  (<font color="#a020f0">if</font> optimized
      (solve-optimized (make-chessboard size-xy) start-x start-y 1)
      (solve-brute-force (make-chessboard size-xy) start-x start-y 1)))</pre>
<pre></pre>
<pre>CL-USER&gt; (time (print-table (knights-tour)))
9 |6 |11|44|27|4 |29|34
--+--+--+--+--+--+--+--
12|43|8 |5 |46|33|26|3
--+--+--+--+--+--+--+--
7 |10|45|48|55|28|35|30
--+--+--+--+--+--+--+--
42|13|54|63|32|47|2 |25
--+--+--+--+--+--+--+--
53|64|49|56|1 |58|31|36
--+--+--+--+--+--+--+--
14|41|62|59|50|19|24|21
--+--+--+--+--+--+--+--
61|52|39|16|57|22|37|18
--+--+--+--+--+--+--+--
40|15|60|51|38|17|20|23</pre>
<pre>Evaluation took:
  0.006 seconds of real time
  0.004001 seconds of user run time
  0.0 seconds of system run time
  0 page faults and
  1,043,200 bytes consed.</pre>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/18/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/18/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/18/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/18/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/18/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/18/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/18/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/18/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/18/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/18/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/18/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/18/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=18&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2006/07/07/solving-the-knights-tour/feed/</wfw:commentRss>
		<slash:comments>20</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>
	</item>
		<item>
		<title>A New Toy</title>
		<link>http://anthonyf.wordpress.com/2006/07/03/a-new-toy/</link>
		<comments>http://anthonyf.wordpress.com/2006/07/03/a-new-toy/#comments</comments>
		<pubDate>Mon, 03 Jul 2006 03:11:49 +0000</pubDate>
		<dc:creator>anthonyf</dc:creator>
				<category><![CDATA[Emacs]]></category>
		<category><![CDATA[Gadgets]]></category>
		<category><![CDATA[Lisp]]></category>

		<guid isPermaLink="false">https://anthonyf.wordpress.com/2006/07/03/a-new-toy/</guid>
		<description><![CDATA[I purchased a new toy yesterday that I&#8217;m pretty excited about, a Treo 700p.  I&#8217;ve been using Palms devices since they were made by 3COM.  The main reason I stuck with them for so long is they are very well supported in Linux.  Palm also makes a 700w which runs the Windows [...]<img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=17&subd=anthonyf&ref=&feed=1" />]]></description>
			<content:encoded><![CDATA[<div class='snap_preview'><br /><p>I purchased a new toy yesterday that I&#8217;m pretty excited about, a <a href="http://www.palm.com/us/products/smartphones/treo700p/">Treo 700p</a>.  I&#8217;ve been using Palms devices since they were made by 3COM.  The main reason I stuck with them for so long is they are very well supported in Linux.  Palm also makes a 700w which runs the Windows embedded OS.  My friend Keven tells me he read a review that said the 700p has a more intuitive interface over the 700w.</p>
<p>So this Treo is 3 devices in one:  a phone, a camera and a palm pilot.  Those items purchased separately would probably run about $399, which is what the Treo cost me.  Having them all in one device really beats the alternative, which surely involves some kind of fanny pack <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_wink.gif' alt=';-)' class='wp-smiley' /> </p>
<p>Today I installed an open source SSH client on the Treo and was able to connect to my Debian server and run Emacs/Slime on the tiny 320&#215;320 screen.  My Treo is now a little Lisp Machine <img src='http://s.wordpress.com/wp-includes/images/smilies/icon_smile.gif' alt=':-)' class='wp-smiley' /> </p>
<img alt="" border="0" src="http://feeds.wordpress.com/1.0/categories/anthonyf.wordpress.com/17/" /> <img alt="" border="0" src="http://feeds.wordpress.com/1.0/tags/anthonyf.wordpress.com/17/" /> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gocomments/anthonyf.wordpress.com/17/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/comments/anthonyf.wordpress.com/17/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godelicious/anthonyf.wordpress.com/17/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/delicious/anthonyf.wordpress.com/17/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/gostumble/anthonyf.wordpress.com/17/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/stumble/anthonyf.wordpress.com/17/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/godigg/anthonyf.wordpress.com/17/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/digg/anthonyf.wordpress.com/17/" /></a> <a rel="nofollow" href="http://feeds.wordpress.com/1.0/goreddit/anthonyf.wordpress.com/17/"><img alt="" border="0" src="http://feeds.wordpress.com/1.0/reddit/anthonyf.wordpress.com/17/" /></a> <img alt="" border="0" src="http://stats.wordpress.com/b.gif?host=anthonyf.wordpress.com&blog=179712&post=17&subd=anthonyf&ref=&feed=1" /></div>]]></content:encoded>
			<wfw:commentRss>http://anthonyf.wordpress.com/2006/07/03/a-new-toy/feed/</wfw:commentRss>
		<slash:comments>3</slash:comments>
	
		<media:content url="http://0.gravatar.com/avatar/6ceed633057ef2a85c19d4e5003d8f0c?s=96&#38;d=identicon&#38;r=G" medium="image">
			<media:title type="html">anthonyf</media:title>
		</media:content>
	</item>
	</channel>
</rss>