Learning Lisp

The Road To Lisp

Archive for May, 2006

Beginning of Bag Project

Posted by j1p on May 5, 2006

So I started working on implementing the Bag project in Lisp.

I've got most of the basics of the class done, in the following code:

 (defclass bag ()
    :accessor get-bag
    :initform ()
    :initarg :itemlist
    :documentation "A list of items in the bag")
    :accessor get-bag-max-weight
    :initform 20 :type integer
    :initarg :max-weight
    :documentation "The maximum weight that the bag can contain")))

(defvar *list-of-bags*
  "List of Bags")

(defun make-bag (&optional (itemlist ())(max-weight 20))
  "Makes an instance of class bag and pushes it into *list-of-bags*"
  (setf *list-of-bags*
     (make-instance 'bag :max-weight max-weight :itemlist itemlist)

(defmethod bag-weight ((bag bag))
  (eval (cons '+ (get-bag bag))))

(defmethod add-item ((bag bag) (item integer))
  (cons item (get-bag bag)))

I still need to implement the function to go through a file, and put all integers in the file into the first bag that it will fit in, and the function to print out the bag. I'm not familiar with reading from files in Lisp, but I assume it should be relatively simple. I've skimmed through the chapter on files and file-io of Practical Common Lisp, and it mentions two functions, read-char, read-line, and read, and it looks like the one that will be most helpful to me will be read. The loops to go through and print/pack the bags will probably use a FIRST of a NTHCDR of *list-of-bags*.

Please, if you have any suggestions/fixes for what I have, let me know, im just learning and don't want to start up any bad habits. For example, I haven't exactly seen the reason to have defgeneric's instead of defmethod's, but I'm sure there is one.


Posted in Bag Project, Lisp | 5 Comments »

Re: Don’t Study, Do.

Posted by j1p on May 3, 2006

I think the Lisp bug has bitten me.

After an uneventful morning, consisting of daydreaming through class and a quick lunch, I rushed to get to work on time. Now, I really do enjoy working here, I tend to look forward to the 3 hours a day I get to spend on a computer, hacking away(normally at html, ColdFusion, or CSS) without being interrupted by neighbors, etc, but I'd rather be doing some other things. I get to work, and to my surprise my 3 co-workers all seemed to have taken the day off. I got through all the webteam stuff in 30 minutes, so I figure I might as well read up a bit on Lisp.

While browsing technorati, I came across a post, How To Advance in InfoSec: Don't Study, Do. While this post has little to do with Lisp in general, it is extremely relevant to what I'm doing here. Here's a quote straight from the post(actually the only part that even mentions Lisp):

Don’t read three books in a row on Lisp. Take a program you’ve written in a previous language and redo it in Lisp. Use your three books as a reference.

That was exactly what I was doing, I checked out 3 books on Lisp, and was reading through them like a tutorial. I need some real experience working with Lisp, making it do something I want it to do, not just what they tell me it can do.

So, I'm going to try to rewrite my first CS102 assignment from Java to Lisp. Here are the details as posted by my professor.


  1. You need to create a class called Bag that contains an array of items. You may assume that the items are all integers (the weights of the various items in pounds) and that the capacity of the bag is twenty pounds. Your private variables will include this array of integers, a count of how many items are in the array, and any other data you feel you will need. The methods for the class should include the any constructors that you will need, any query functions (such as examining the weight currently held in the bag), and a method to insert a new item into the bag. You may, of course, include any other methods that you feel you need.
  2. Your input will be a list of integers. You may read it in from the screen or from a text file (a text file is probably easier). If you read it in from a text file, be sure to prompt the user for the name of the file that is to be used for the input. If you input the weights from the screen, be sure to give the user sufficient prompts. If any bad data (such as a character) is in the input, ignore it and proceed to the next input.
  3. If your input is: 15 13 4 9 6 1 , for example, your output should be of the form:

    Bag 1: 15 4 1

    Bag 2: 13 6

    Bag 3: 9

  4. You should create a second class for packing the bags that contains a method called pack(), which reads in your data and packs them into the bags. You will need a method to print your results, which calls a print method in the bag class. Your main method should be very short, essentially calling pack() and print().

  5. Be sure to include comments in all of your methods

Alright, so this looks like it is going to be much simpler in Lisp than in Java, for the fact that practically all it is is list manipulation, Lisp's specialty. I have no need to make the Bag class contain an array of items, it can simply be a List of items in Lisp.

To make this work as close to the specifications as I can, I am going to need to learn more about CLOS, though most of the methods for the classes look like they will be pretty simple.

I have a 10 page paper to write for class tomorrow, but I'll probably hold that off until after I get home and use SLIME to write up some preliminary functions that will help for the final Lisp-version of Bag.

Posted in Bag Project, Learning, Lisp | Leave a Comment »

Lisp Web Applications

Posted by j1p on May 3, 2006

After a bunch of reading on implementations of Lisp solutions, and thinking a bit about how I would benefit the most from learning Lisp, I have decided I should look at it in the perspective of web-based applications.

It seems that any program I could develop(not that I am in any way ready to develop a distributable program) would be limited to Linux machines, which is not exactly the best way to reach users. I will, of course, learn the basics that would necessary to develop these applications, but I think I will take on the web-based perspective.

After realizing this, I looked at a few solutions for Lisp on the web. Things such as the UnCommon Web, TBNL, and Araneida. You may remember the question I posed at the end of the last post, about which Common Lisp implementation a beginner Lisper(is that the right term?) should use. With these solutions being some of the most common possibilities, I chose SBCL, for a variety of reasons. For one, these Lisp Web Servers seem to integrate very well with SBCL. Another reason is SBCL seems a powerful, popular CL implementation, with features such as threading.

I plan to set up some kind of local test server running one, or a combination of these solutions on my Ubuntu box in the next two weeks, as my semester at University is ending. Speaking of school, after next year I will have fulfilled the prerequisites to the AI and Robotics classes, both of which touch on Lisp, and are taught by a very knowledgeable professor.

Now, back to my road to learning the skills I actually need to complete any of my various dreams of hacking in Lisp:

At work this morning I sat down and read through the first few parts of The CLOS Perspective, which was my first introduction to object orientated programming in Lisp. Unfortunately, the book is not very focused on "teaching" how to program with CLOS, but by the few code snippets in the first few sections, it looked pretty simple, and similar to defining functions, with a little more added. I'll have to find a better book on teaching CLOS, or an online tutorial of the sort.

I've read through the parts of Steele's book that correspond to the points I've learned through Winston and Horn's Lisp. In Lisp, I've finished Chapters 2 and 3. I've learned all about association lists, some more advanced mathematical functions (round, expt, sqrt, abs, max, min) by finishing chapter 2, and believe I've mastered the (simple) list manipulation functions.

Here are the rest of the sample problems from Chapter 2:

Problem 2-8: Evaluate the following forms

  1. (length '(plato socrates aristotle))
  2. (length '((plato) (socrates) (aristotle)))
  3. (length '((plato socrates aristotle)))
  4. (reverse '(plato socrates aristotle))
  5. (reverse '((plato) (socrates) (aristotle)))
  6. (reverse '((plato socrates aristotle)))

Problem 2-9: Evaluate the following forms

  1. (length '((car chevrolet) (drink coke) (cereal wheaties)))
  2. (reverse '((car chevrolet) (drink coke) (cereal wheaties)))
  3. (append '((car chevrolet) (drink coke)) (reverse '((car chevrolet) (drink coke)))) — hard to format correctly, sorry!

Problem 2-10: Evaluate the following forms

  1. (/ (+ 3 1) (- 3 1))
  2. (* (max 3 4 5) (min 3 4 5))
  3. (min (max 3 1 4) (max 2 7 1))

Chapter Two Summary (main points)

  • LISP means symbol manipulation
  • LISP procedures and data are symbolic expressions
  • Lists are like bowls
  • FIRST and REST take lists apart
  • Quoting stops evaluation
  • Some "old timers" use CARs and CDRs
  • SETF assigns values to symbols
  • SETF accepts multiple symbol-value pairs
  • Certain atoms evaluate to themselves (t and nil)
  • CONS, APPEND, and LIST construct lists
  • CONS, APPEND, and LIST do not alter symbol values
  • NTHCDR, BUTLAST, and LAST shorten lists
  • LENGTH and REVERSE work on top-level elements
  • ASSOC looks for indexed sublists
  • LISP offers integers, ratios, and floating point numbers, among others
  • A few primitives for numbers round out a basic repertoire

Chapter 2 was basically a run-down of what I had already learned through the first few chapters of online tutorials, so it didn't challenge me much, and Chapter 3 was also mostly the same. Chapter 3, titles Procedure Definition and Binding, introduced functions, and the Lisp primitives; defun and let.

I don't have much time to cover Chapter 3 tonight, as I have 3 papers and 4 finals in the next two weeks, and its getting late. I'll try to post about chapter 3 and anything I read tomorrow by Thursday.

A question for you readers(if you exist): Which setup of a Lisp webserver would you recommend me. I have set up a few Apache2 servers before, so I have some experience in the area, but would prefer a not-impossible set-up, and decent feature-set. As I am just learning, I obviously don't need features that would only benefit the most advanced of applications, but it would be nice to have some power while building my skills.

Answers to sample problems in last post(please correct me if I get some of the wrong, I am just learning):

Problem 2-1:

  1. Atom
  2. List(of the atoms THIS, IS, AN, ATOM)
  3. List(of the atoms THIS, IS, AN, EXPRESSION)
  4. Neither(ill formed parenthesis)
  5. List(of the atoms LIST, 3)
  6. List(of the atom /, and Lists (+ 3 1) (- 3 1)
  7. Neither(ill formed parenthesis)
  8. List(of a List of a Empty List)
  9. List(of two empty Lists)
  10. Neither(closing parenthesis don't match opening parenthesis)
  11. Neither(ill formed parenthesis)
  12. Neither(no closing parenthesis)

Problem 2-2

  1. P
  2. (K P H)
  3. (A B)
  4. (C D)
  5. (C D)
  6. (B)
  7. (D)
  8. B

Problem 2-3

  1. D
  2. E
  3. (A B)
  4. This gave me an error when I put it into SBCL, The value REST is not of type LIST.
  5. FIRST
  6. (FIRST (FIRST (REST (REST ((A B) (C D) (E F))))))

Problem 2-4 (assume *list* is set to the list in question.

  1. (first (rest (rest *list*)))
  2. (first (first (rest *list*)))
  3. (first (first (rest (rest *list*))))
  4. (first (first (first (rest (rest *list*)))))
  5. (first (first (rest (rest *list*))))
  6. (first (rest (first *list*)))

Problem 2-5

  1. (A B C)
  2. ((A B C) NIL)
  3. ((A B C))

Problem 2-6


Problem 2-7

  • (NIL)

Posted in Learning, Lisp | 2 Comments »