I'm trying to build up my Common Lisp vocabulary by looking through code examples and noting commonly used functions and idioms. Since CL has been around for awhile, I was wondering if anyone had some pointers to particularly good examples of applications or libraries that would be better for study.Thanks so much!

I've always liked cl-ppcre as an example. It covers many different features of Common Lisp, it does an interesting job, it's well-commented and well-documented, it's challenging but not impossible to understand, and it's very fast.

xach wrote:I've always liked cl-ppcre as an example. It covers many different features of Common Lisp, it does an interesting job, it's well-commented and well-documented, it's challenging but not impossible to understand, and it's very fast.

Yes, agreed. It has a neat way of compiling the regex into code using closures to do the heavy lifting. Frankly, anything written by Edi is going to be well-written and a good education, but cl-ppcre is great in that regard.

Another thing that's worth considering is that most CL implementations are largely written in CL (which can get pretty hairy in cases where the origins of the system are hidden under a lot of years of bootstrapping- CMUCL comes to mind). So you might find it interesting to look at how certain parts of the open source CL systems are implemented, and compare them. It's a bit ambitious, but I think you might find it very interesting to read AMOP and then compare CLOS implementations. I think most of the open source CLOS implementations have a common ancestor, but they've diverged a bit.

I think you might also benefit from looking at how the standard CL data structures are implemented in CL. One of the great things about- well, not just CL, but quite a few modern languages, is that you can do a lot with the built-in data structures. I do sometimes worry that this encourages a sort of two-tiered organization of programmers, wherein a small group of programmers knows how to implement a hash table, say, and a large group knows how to use one. The problem with this isn't just that we might arrive at a point where no one remembers how to implement a hash table (or implement CMUCL from the ground up) a la the famous Asimov story (seems kind of unlikely, actually, at least when it comes to hash tables ).

Eventually the built-in data structures are not going to be optimal for what you want to do, and you're going to want to implement some new ones. And that can be tricky even if you've done it before in, say, C. Cl is pointers, under the covers, and C is pointers above the covers, so you wouldn't think there would be much difficulty there, but I found that adjustment a bit tricky. There's a well-established idiom when it comes to doing this sort of thing through direct pointer manipulation in C, one that I was familiar with because I had had to implement these sorts of things, starting with linked lists, but in CL.. well, maybe I am just thick. Anyway, past the built-in data structures a number of libraries have popped up over the last few years for things like AVL trees, red-black trees, etc. You probably don't need a huge number of examples to figure out the basics of the idiom in this case, but a few could hardly hurt.

I've been flicking (very briefly, I haven't even begun to understand it yet) though ppcre, and one thing I've immediately noticed is that a few of the functions are HUGE. For example, in convert.lisp the function convert-aux is over 500 lines long. I understand that lines in lisp are even less of a useful count of a program's length than they are for other languages, but even so, that's huge!

As a C++ programmer I tried to keep to the saying "never write code that is bigger than your head", with the size of your head being the physical size when pressed against the screen: something like 60 or 70 lines. Whenever I found myself writing a function longer than that I just split it down into several different functions, which I could get an idea of what they did just by looking at their names. That way I can get a feeling for how a function works just by glancing at the code.

Are things different in lisp? Is it not considered bad style to write massive functions? And if so, why?

dbdkmezz wrote:I've been flicking (very briefly, I haven't even begun to understand it yet) though ppcre, and one thing I've immediately noticed is that a few of the functions are HUGE. For example, in convert.lisp the function convert-aux is over 500 lines long. I understand that lines in lisp are even less of a useful count of a program's length than they are for other languages, but even so, that's huge!

Huh? I just checked, cl-ppcre::convert-aux is four lines long. I haven't ever really read the cl-ppcre sources, but from what I can see there are a few quite long functions, but they are mostly an enumeration of cases, and I don't think they would cleanly separate, and a few others which appear longer due to comments

dbdkmezz wrote:Are things different in lisp? Is it not considered bad style to write massive functions? And if so, why?

It is good style to write short functions, but this, as always, is more a guideline than a rule. If the function really doesn't decompose, then breaking it up would only cause more confusion. Of course that is rather subjective, but so are most style issues.