Archive for August, 2007

“Improve Code Configurability” Afterbirth

August 31, 2007

Well, my last post generated a fair amount of feedback. I was surprised at how well the choice of using Traveller for a coding example went over. Two people on reddit up modded it just for that reason, while a guy on del.icio.us simply tagged his link with “has an example of Traveller world generation– kickass.”

While it was apparent to the hard core Lisp crowd that I “wasn’t very experienced in Lisp,” the old timers had to “give me credit for trying.” One lisper give me “props for implementing [my] own infix syntax instead of complaining about prefix syntax on Usenet.” This slightly patronizing response is actually a step in the right direction: the last time I ended up with a “hawt post” my poorly crafted ramblings (peppered with hyperbole no less) spawned a minor language war that forced a more experienced lisper to come in and set the record straight. Even Paul Graham had to drop in to correct my code! I was clearly out of my depth back then, but I at least learned in the process that a good blog post should be written so that inexperienced readers can easily pick up on what you’re talking about while at the same time you should make sure that expert readers are not put off by imprecise or incorrect language. When I was first writing, I really had no idea who my audience was… or even that I could have one… but apparently in blogging you can find out a lot about your audience quickly.

As before, I continue to (inadvertantly) insult Peter Sieble with my off hand remarks. The discussion of “entry level” Lisp books is not going to go away, so I’ve got to do something about this. I think I will have to try the PCL experiment. It works like this: carefully read PCL from cover to cover. Think up a short project to work through, code it, and then write a blog post about it. Finally, check the feedback on it and try to get a feel for whether or not my techniques are acceptable to the “real” Lisp programmers. If there are fewer patronizing “well, at least he’s trying” type remarks, then PCL must be the mack daddy of Lisp books.  ;)

Oh, one last note for those that need an inspiring thought to keep them motivated in their quest to master Lisp. One nit-picker over on reddit had to point out that not only was my technique not limited to working in the Common Lisp dialect, but that I was merely specifying a DSL and then coding an interpreter for it– something that could be done in just about any language! When I answered back that the point was that Common Lisp makes writing embedded languages intuitive and natural even for intermediate level coders, he responded: “Having the foresight, imagination, and experience of implementing a DSL requires a learning curve which is far beyond the average enterprise programmer of today. They are far more likely to consume an entire bookshelf of books about other people’s DSLs than they are to ever construct one.” And that’s why you’re investing such effort into learning Lisp: you want to spend your time mastering skills that will set you apart from the “average enterprise programmer.” Thanks to the unusual features of the Lisp language and the extremely high quality of materials on it by people like Paul Graham, Peter Norvig, and Peter Seibel you can achieve that goal in a matter of months. Don’t give up, guys!  Illumination will soon strike you like lighting out of a clear sky!

How Basic Common Lisp Techniques Can Improve Code Configurability, Maintainability, and Reuse

August 29, 2007

“Lisp programs inflate libraries with functions whose utility transcends the application that produced them. The list, Lisp’s native data structure, is largely responsible for such growth of utility. The simple structure and natural applicability of lists are reflected in functions that are amazingly non-idiosyncratic…. It is better to have 100 functions operate on one data structure than to have 10 functions operate on 10 data structures.” — Alan J. Perlis

You might have started out with Peter Seibel’s Practical Common Lisp. You thought of yourself as being an experienced coder, so you skimmed it quickly, mainly taking away the point that Lisp really is unusually expressive and powerful. But after sitting down at the REPL prompt you succeeded at only kludging together ugly imperative style programs. So you slowed down and worked through half or more of a more straight forward tutorial. This lead to a pet project that started innocently enough, but that soon spun out of control and got uglier and uglier as you took more and more shortcuts just to get things to work. Maybe you dipped into some more advanced books and solved some clever problems, but you want to start coding something real because you’re beginning to lose interest. As Duncan Kenzie said, “any time you have something that can give you good success early on, it helps to build momentum and get into more complex things.” Without something resembling a successful project, you’re liable to give up on Lisp and go off and tinker with Python or Ruby instead. This article is written in hopes of preventing such a fate for the would-be Lisp programmer.

What we’re going to do is demonstrate how the plain vanilla Common Lisp list can adapt to just about any data structure you can think of. We’re going to use a simple list to write pseudo-code that is designed to be as readable as possible– then we’ll build up on our core language elements until we can actually run our pseudo code. We’re going to do all the things that the Lisp experts have bragged about (and that you’ve maybe failed to achieve on your own) and we’re going to show that you don’t have to be a genius to make this work for you. In fact, the most difficult technique we’re going to use is recursion on trees and lists– something that most Lisp texts tend to confront you with fairly quickly anyway. We’ll see that while it may take us a little bit longer to work through a problem than it would, say, in a language that we’ve already mastered, it will all be worth it for the additional configurability we get in the process.

The Problem: Traveller World Generation

“The referee has the responsibility for mapping the universe before actual game play begins. The entire universe is not necessary immediately, however, as only a small portion can be used at any one time.” — Traveller Book 3

Whenever I’m experimenting with a new technique I like to do something completely and pointlessly fun. The less “real world” applicability, the better. (Of course, nine times out of ten, I end up applying the techniques I learn on a real project later on, anyway.) For this project we’ll dig back into the pencil and paper gaming scene of the late seventies and look at the world generation sequence of the first science fiction role playing game. The game Traveller debuted in 1977. It featured a generic space opera setting that was vaguely reminiscent of classic sci-fi works such as Dune and the Foundation series. Actually, it didn’t originally come with a fleshed out setting at all: the “referee” was supposed to randomly generate one for the players to explore. Back in the day, this meant hours of rolling dice and penciling in obscure symbols on retro-nerdy xerox copies of professional-looking interstellar “TAS forms.”

You can get an overview of the process by looking at this pseudo code snippet. Size represents the world’s planetary diameter in thousands of miles. You roll two six sided dice and subtract two to determine this property. (A zero here signifies a “world” that centers in and around an asteroid belt.) To determine the Atmosphere code for a world, roll 2d6, subtract 7, and add the value we determined for Size. Just as Atmosphere is influenced by Size, so is the Hydrographics code influenced by Atmosphere. Likewise, Government type is influenced by the Population code and Law Level is influenced by the Government type. Note that, the Population of a world is completely independent of the world’s environment. You can end up with an airless rock-ball with a population in the billions right next to a garden world with a population in the hundreds. While many Traveller players complain that such results are silly, others took great delight in attempting to come up with plausible explanations for such anomalies. In any event, referees are encouraged to throw out any results they don’t like, and there are only so many worlds that can be successfully managed in a real game anyway.

To write a program to take care of all of this is pretty trivial. All we need is a way to pull the rule expressions out of our pseudo-code list. Once we have the expression, we need to massage it so that the “2d”‘s are replaced with randomly generated die-rolls and the field references are replaced with their current value. Once we’ve made such a pass over our expression list, were left with a simple arithmetic problem. Writing a recursive function to perform that calculation is pretty straight forward, and once we put all of these pieces together in our create-world routine, we have a working proof of concept. The following code snipped from the REPL prompt demonstrates our program in action:

CL-USER> (get-rule (third *worlds*))
(|2D| – 7 + ATMOSPHERE)
CL-USER> (massage (get-rule (third *worlds*)) ‘(1 2 3 4 5 6))
(11 – 7 + 2)
CL-USER> (massadd *)
(6)
CL-USER> (create-world)
(2 5 6 3 6 2)

We’re glossing over a few details here, but if you have a little experience working with Lisp then you should have a pretty good idea of how to implement the above. The get-rule function returns a list containing everything after the -> symbol in an item from our list of pseudo-code expressions. The massage function is a little trickier. While it’s trivial to replace occurrences of |2D| with the results of simulated die rolls, to substitute the correct numbers for the reference Atmosphere we’re going to need to pass along a list such as (1 2 3 4 5 6) above representing each of the world code values. The code will have to pull the correct value from the list and then substitute it for the ATMOSPHERE tag. Massadd moves through the list replacing occurrences of [0-9] [+-] [0-9] with an integer. The create-world function starts with a blank world description (0 0 0 0 0 0) and then cycles through each position replacing it with the results of evaluating massage and massadd with the corresponding line of pseudo code. Simple!

Notice that everything we’re doing is in terms of cycling through lists. Everything we do can be conceived of in terms of abstract operations on lists. Each function that we write to accomplish the above is fairly straight-forward… but this a completely alien approach when compared with how we tend to do things in more imperative languages.

There’s More To It Than That

Okay, it’s actually a little more complicated than what I’ve described so far. This is the seventies, we’re talking about here! This is RPG’s, even…. You aren’t having real fun unless you’re rolling dice and looking things up on charts and tables. (See this pseudo code file for a better idea of what we’re dealing with.) For Starport type and for checking for the existence of Bases and Gas Giants, we need to roll two dice and look up the result on a chart. To find out the TechLevel, we need to cross reference most of our World codes on a table and add up the values. There’s probably a more concise way to phrase this, but this was about as simple as I could make it. I came up with a simple way to inline all but two of these tables with their respective rules. The :choose directive takes a number parameter and returns the nth item on a list. The :table directive does the same thing in a more verbose (and more flexible) manner by looking up a value in an associative list. Also, we’re going to have to make sure that some of our world codes fall within a specified range.

CL-USER> (masschoo ‘(:choose 5 [ABCDEFGHIJ]))
(E)
CL-USER> (massage ‘(1d + :choose Size + 1 [22111000000]) ‘(A 2 0 0 0 0 0 0 0 0 0 0))
(4 + :CHOOSE 2 + 1 [22111000000])
CL-USER> (massadd *)
(4 + :CHOOSE 3 [22111000000])
CL-USER> (masschoo *)
(4 + 1)
CL-USER> (massadd *)
(5)

In the above example we see the new masschoo fuction demonstrated from the REPL prompt. First we “choose” the fifth item from a string contained inside square brackets. Then we step by step break down a more complex piece of pseudo-code step by step. First we “massage” the die roll and substitute a 2 for the Size tag. Next we replace the 2 + 1 with a 3 using our previously written massadd function. Then we choose the third item from our string of results. And finally we “massadd” the resulting list to get our final result of a 5. Note that the massadd and masschoo functions are easily tested from the REPL prompt and that it’s trivial to come up with test cases that prove they work correctly. And now that we have them worked out, they are so generic that they could easily be applied to totally different projects. If you’re still wondering when you’re going to get around to experiencing the much-vaunted benefits of code reuse in your OOP applications, then maybe Lisp can provide you with a model for achieving it a lot sooner!

Good News, Bad News, How to Reinvent the Wheel!

It seems like every project has one thing that is completely unanticipated. You know… the kind of nightmares that cause you to reflexively multiply all of your coding estimates by a factor of 5. (Check out this pseudo code file to see what we really needed to be able to work with from the start.)  In this case, just as I thought I had completed my project in record time (and with hardly any short-cuts or kludges even) I reread the rules and to find out that I’d missed some essential logic in the pseudo code. I actually needed to be able to handle conditional logic in the same style with which I’ve dealt with table look ups and die rolls…. Now if I’d known I was going to do this much work, I probably would not have started the project quite this way. I don’t know what I’d have done… maybe I wouldn’t have started the project at all. Anyways, I decided to suck it up and hack through the problem anyway. I just about ended up doubling the code size for the project in the process, but I think some of that is due to the fact that I was reinventing the wheel in places. Maybe if I was more familiar with the built-in functions of Common Lisp, then I might have had an easier time.

CL-USER> (massif ‘(:if [ 0 = 0 ~ 5 ~ 42 ]))
(5)
CL-USER> (massif ‘(:if [ 2 = 0 ~ 5 ~ 42 ]))
(42)
CL-USER> (massif ‘(:if [ 2 = 0 ~ 0 ~ 5 – 7 + 6 :if [ 6 ranges from 3 to 8 ~ - 4 ] ]))
(5 – 7 + 6 :IF [ 6 RANGES FROM 3 TO 8 ~ – 4)
CL-USER> (massif *)
(5 – 7 + 6 – 4)
CL-USER> (massadd *)
(0)
CL-USER> (massif ‘( (:if [ 2 <= 5 ~ AA ] :if [ 3 = 6 ~ BB ] :if [ 7 in ‘[2579] ~ CC ]) ))
((AA CC))

Here we see my (perhaps half-baked) list oriented “embedded if” concept in action. I wanted to avoid introducing nested parentheses to the pseudo code due to all the hard feelings they seem to generate in non-lispers. I used the ~ character to represent the argument separator. So the first example expresses “if 0 equals 0 then return 5 otherwise return 42.” Of course, we may need to return expressions… and we may even need to return expressions containing more :if directives. Finally, we may need to return a list of items, with each item associated with their own conditional that determines whether or not the show up in the list. Coding all of this didn’t require any advanced techniques beyond the usual recursion on lists and trees, but it did require a lot of tedious work to get a function that could handle all of the various cases. Whenever I expend this much effort on something like this I always assume I’m overlooking something obvious, but the time it would take to figure out what that was exactly might (in this case anyway) take longer to figure out than it would to just follow my original premises to their logical conclusion. Not as pretty as I would like, but you can always expect a few rough edges when you’re trying to pick up a new language.

Here we have a demo of the final program:

CL-USER> (create-world)
(B 8 8 1 8 6 4 – 5 ~ S G (RI))
CL-USER> (create-world)
(A 4 5 0 4 3 0 – 12 ~ S G (NI PO DE))

In that last result there, you can see the that we have a Starport code of A, Size 4, Atmosphere 5, Hydrographics 0, Population code 4, Government code 3, Law level 0, Tech level 12… there’s no Naval Base, but there is a Scout Base and a Gas Giant. Finally we have Trade codes Ni, Po, and De. Each position in the list corresponds to a result derived from a line of pseudo-code.

Conclusion

Lets take a quick look at what we got using this approach to solve our problem. (Here’s the complete code listing.) First, the program logic for the overall thrust of the application fits neatly into a single screen. This is extremely handy if you want to attempt to keep the entire program in your head at once. (Note that habits developed while working with relational databases and modern OOP languages work against this outcome: those tools train you to break each piece up into their own separate table or code file.) The pseudo code practically eliminates the need for code comments to document what’s going on. Not only are we at the opposite extreme of Perl’s notorious “right once read never” methodology, but we can also make complex changes to the behavior of the application without writing new functions. We can add new “properties” to our world objects without modifying any class definitions and we can open up our program to customization– even to people with an innate fear of parentheses! Finally, the list processing routines can be reused in completely different applications. In fact, the bulk of our code is more like abstract utilities than anything else.

So we have realized most of the promises of the Lisp advocates. Paul Graham was right when he said that “in Lisp, you don’t just write your program down toward the language, you also build the language up toward your program.” And notice that we could do it without using the hard-core techniques like closures and macros that get all the press. We could do it just using recursion and the built-in features of the humble list. The key to our approach was not to think of our processes in terms of tables or objects or any other abstraction… but to instead try to express the problem as closely as possible to a natural pseudo-code notation. We then built up our language to the point where we could actually execute the pseudo code. While it was challenging to work out a few of the list processing routines, integrating our new language elements into the pseudo-code interpreter turned out to be a snap.

This approach may not be suited to everything you might want to code, but if readability, code reuse, and configurability are really important to you, this might be the way to go. At any rate, programming this way is a lot more fun!

Okay… questions anybody? Yes… you over there in the “I grok Spock” shirt….

“But what about speed and efficiency?”

It may appear inefficient to make so many passes across each “rule” list in this example. If speed matters, what we can do is alter our approach somewhat by developing a macro that transforms a pseudo code rule into a function. These could then be compiled at run time, and our code will run about as fast as if it were all written directly in Lisp.

Yes. Thank you. Okay, you over there with the trendy Buddy Holly glasses….

“What’s the next step in developing the application?”

Assuming that the premise of this program is not insane, the next step would be to write a set of thorough unit tests for our existing language elements. Once we have the functions working correctly for all of the oddball cases, then we should look at adding some additional elements that improve the expressiveness of our custom pseudo code language. In particular, I would like to have a :table directive that could process more complicated table look ups. (I don’t like having to have a separate associative list defined for the Government Tech and Starport Tech modifiers tables.) Another thing to do is to carefully read the Common Lisp specification to help eliminate anywhere that I’m inadvertently reinventing the wheel. We’ll want to look at our functions and try to determine if there’s a way to make any of them even more generic than they already are so that when we pull them out into a utility file they’ll be more useful in other programs. Finally, we’ll want to look at other world generation procedures and see if they can be implemented in our pseudo code without having to extend the language anymore. Once we get that far, we know we’ve accomplished something.

Okay… you in the turtle neck there….

“Yeah, uh, can’t I program in a similar style in the language I aleady use?”

Yes you can. I’ve coded similar applications in other languages myself. The thing is, I started by googling for a utility that could evaluate strings into code. It took me maybe a few minutes to extend the application with my own “instant if” function and things like that… but there’s still this chunk of code there that I shamelessly munged off of someone else and that I might not completely understand. In other languages you’re much more likely to hack out a kludgey mess that only works well for a single class of problems– so unless you’re really good you’ll lose out in the code reuse department. When you work with Common Lisp, you get a code evaluator out of the box for free and you’re working with the overall idiom of the language. You might spend a little more time working through some of your custom functions, but you end up with something that is completely transparent, understandable, and generically applicable.

Attempting this in other languages, there is a tendency to create applications in which you have an evaluator that’s tacked onto (and hardwired for) a bunch of other code. Notice that the way we worked here, we didn’t end up with an evaluator that was tacked on to a bunch of other stuff. The evaluator was our program. Once you begin to think in these terms, you can begin to develop applications which blur the lines between “data” and “code logic” in a much more creative manner. It is this property that makes coding in Lisp so much fun.

Update 8/30/07: A lisp hacker has rewritten my code to take advantage of more of the language’s native features– eliminating a great deal of code in the process. While the new iteration of the pseudo-code might be less non-lisper friendly than what I would prefer, you can still see a few places where I coded a function that already existed in the language.

Update 8/31/07: I respond to feedback on this article here.

Master Fundamental Hacking Principles with Scheme

August 21, 2007

“If you don’t understand the principles, or if you are the kind of person who wants to be given a cookbook of what to do rather than to think creatively, or if you only want to work on problems that are pretty much like the problem you worked on last time, then this approach will not work for you. There are other approaches that will be more reproducible for a limited range of simple problems, but there is no better way than SICP to learn how to address the truly hard problems.” — Peter Norvig

Michael Harrison is looking to kick off an online SICP study group that will work through the MIT’s open courseware materials from September 5 to December 12.  If you get stuck working through the difficult Lisp books on your own (or if you get distracted with other topics because you don’t have a study schedule) then you might benifit by joining such a group and having folks to bounce ideas off of.

Of course, you could always try working through the book by youself and post lame blog entries about how it’s so hard to get through it on your own… but come on… you’re not only going to irritate the online Lisp community with your inane ramblings, but you’re not going to get the feedback you need to truly develop your skills that way, either!  (Get a clue… I mean… why don’t you wait until you have something to say before you start posting?!)  So drop Michael a line and join the fun!

Ronald P. Loui: The Best Student AI Work Is Developed in Gawk

August 15, 2007

Here is some surprising evidence that Perl should still be respected in spite of its “indecent” appearance. And while Gawk appears to beat Lisp at its own game in this case, it may in fact be because it has so much in common with Lisp.

Important Gawk Features based on Ronald P. Loui’s AI class experience:

  • Powerful String Processing Language Features
  • Powerful Constructions for Manipulating a Wide Variety of Data in Efficient Ways
  • Interpreted Language with a Short Learning Curve
  • Automatic Initialization, Implicit Coercion, I/O Support and Lack of Pointers
  • Regular Expressions
  • Associative Arrays
  • Relies on the OS to provide Data Organization, Debugging Tools, and Subroutine Libraries
  • Powerful Uniform Data Structure
  • Trivial Syntax
  • Encourages Bottom-Up Design and Exploratory Programming

If you don’t have time to master Lisp, Gawk might be a pretty good substitute….

(I found the link to the above article in the comments of an blog entry that really trashes poor RPG. Just reading through it I noticed a lot people love to make lame complaints about languages they know nothing about. Whether its Lisp or RPG, most of the things people get hung up on have either been addressed in the 20 years since the person last saw the language or that can be addressed by trivial modifications to a text editor. Anyways, old school RPG’s “program cycle” is very similar to the basic premise of gawk– sans most of the more lispy features, of course. RPG’s tight integration to the OS is is also very similar.)

The Path to Enlightenment is Littered With Parentheses

August 14, 2007

Adam Gomaa got quite a ways down the path of Lisp enlightenment, but has been turned off by the tedium of working with his SBCL implementation. He has difficulty with “packaging, setting up an environment, and debugging on the fly” and also with “setf, setq and all of the defvar variants.”

On my end, I’d say that working through the first sections of Shapiro’s CL:AIA got me fairly fluent in using packages. However, for the small projects I tend to tinker with on the side, I don’t find myself wanting to use packages much outside of Shapiro’s exercises. (Working inside packages other than CL-USER fattens up my symbols with a package prefix, I’ve noticed.)  As to setting up an environment, Lispbox on Windows takes most of the pain out of it… and setting up Clisp with Emacs has not proven to be that difficult on Cygwin or Linux even for me. My debugging skills are pretty weak though: I generally just hit the number that corresponds to Abort whenever there’s a problem.

Setq and Setf are no big deal. Setq is a specialized setter for working with symbols. (And remember that symbols aren’t just variables… but are really objects with quite a few properties of their own.) Setf works with anything. For instance, suppose you’re storing a list in a symbol. You could use Setq to set the symbol to be equal to the list you want to work with. And you could use Setf to work with the actual cars and cdrs that make up the list. (Actually, you can ignore the difference between these two most of the time and just use Setf for both purposes.)

Defparameter and Defvar have a similar subtle and ignorable difference. Defparameter is used to set a global variable to a new value. Defvar does the same thing– but only if thevariable does not already have a value! That’s a pretty finicky difference there, and if you’re using Defvar on purpose, you’re probably a lot smarter than me.  (If I’m working out some code, I generally like to be 100% sure about the program state before I start running any routines.) So really you don’t have to worry about these differences unless you’re trying something fancy and you can generally get away with just using Setf and Defparameter.

Given the lack of any recent Lisp posts on Adam’s blog, it appears that the Lisp community has lost yet another neophyte to the swelling ranks of Python advocates. Hopefully he will at least continue hacking away from Emacs. ;)

PCLinuxOS 2007– Ready for Average Joes?

August 13, 2007

It’s a shiny little desktop; very crisp and tight. Firefox is a sweet browser and Synaptic is a great package manager. Sure enough if things don’t look like they work.

But now the bad news for PCLinuxOS 2007:

Weird Behavior: Running from the CD, it there’s a lag between creating new files and having them show up in the GUI. I haven’t reduced this to a set of repeatable steps and I wonder if this is even some sort of Twilight Zone thing or something, but there’s something non-intuitive going on here.

Base: Hey… Open Office has a clone of Access! But going in and creating a table, defining some columns… and hey… how do I set a primary key? Hmmm… can’t. Close the table to save it and I get prompted to add one… it adds a totally new field without giving me a chance to select the field I wanted to be the primary key. Open the table and start entering some rows… and the autonumber field seems to go haywire. Why is this program taking up space on the install??

Stupid question: Why doesn’t the CD Rom drive show up so that I can explore it and tinker with it?

Installation to USB drive is dodgy: The installation wizard seems to be wacked. You start off with an option to install to hard drive or to USB drive. If you select USB, you still see your hard drive on later screens of the wizard. This is particularly frightening on the partitioning screen. Your primary hard drive is the default drive being doctored even if you’ve already told the wizard that you’re doing a USB install.

The install wizard does its thing and then stops without giving a success message or new instructions. This is very confusing. I just have no idea if I’m done or if the wizard crashed or anything.

“Persistent Home” should work by default: After using the system, enjoying it, and setting up a bunch of packages, I shut down the system expecting it to all be there when I come back in. And of course… it’s not there! There appears to be a way to use KPackage and Kusbhome to keep your stuff from boot-up to boot-up, but you apparently have to download and install those packages– and log out and log back in!– in order to get this feature. Even then, installing the functionality is nontrivial and seems to require some special partitions to be set up on your USB drive. (And you seem to have to do this every time you boot up.)  None of the software gives you any obvious assistance in identifying the fitness of your USB drive for these purposes. In my case, I could persist my own files, but I could not figure out a way to persist my installations of Clisp and Emacs from session to session. This stinks all the more when such a feature should work automatically or at least be painless to implement.

IMHO: On logging out or shutting down, I should get a message warning me that I’m about to lose my work… and there should be an easy way to save stuff offered. On boot up I should have an option to use the persisted files in setting up the session.

Conclusion: I gave up on the Persistent Home scenario after wasting hours of time and risking sudden death to my hard drive via an accidental mouse click. I tried to go back and install the OS to the USB drive. Again, it’s not clear if 1 gig is enough space to store the installation and given the poorly designed Wizard, I can’t trust it to tell me such pertinent tidbits.

On my final attempt to make the installation work, I used the Installation Wizard’s partitioning tool to set up three partitions: a 470 MB / partition, a 94 MB Swap partition, and a 415 MB /home partition. The Wizard chugs away briefly on my USB drive and then stops.

I then fire up the Installation Wizard again (after rebooting, I think) and set the install to go to the USB drive to the existing partitions. It then copies files for about 15 minutes or so and then… it just stops. Looking at the drive, there’s boot, home, lib, usr, and root directories on the /home partition. And there’s just a couple files left over from my “Persistent Home” attempts over on the / drive.  Shutting down kicks me to an all-text log-in screen and I have to look up a Unix command to manually shut down the system.  Booting to windows log-in screen and then shutting down strangely leads to the crashing of some random file or memory address.  This is starting to get scary.

I went into the BIOS and moved _USB HDD, USB FDD, and USB CD options to the top three positions of the boot order. There’s a message there saying that “USB BIOS support must be enabled for USB boot” but I don’t know where to go to affect that change on my IBM ThinkPad. Booting up without a DVD in the drive and with the USB stick plugged in leads to a message saying, “Invalid system disk, replace the disk and press any key.”

This is altogether a very frustrating experience. This OS is just slick enough that I want to move to it and use it as much as possible. But I don’t trust the software and fear that I will inadvertently fry my machine with an accidental mouse click. I can only conclude that the USB install is not the default approach that most people use with this platform… and that most people using it tend to set aside a half dozen gig on their hard drive and install there instead.

I’m rooting for this distro and would very much like to be a satisfied non-customer… but at this point I’d have to say that the Wizards and the documentation for the install process are very poor.  Other people seem to have had a good experience with it, but I’m not there yet. From my perspective, I’d have to say that we’re still a ways from having Granny install and use this thing on her own….

Two Reasons to Look for an Alternative to Microsoft Wherever It’s Feasible

August 13, 2007

Microsoft often makes great tools to solve problems that Microsoft frameworks often bring into existence – like a drug company that also manufactures sickness. Many Microsoft tools appear impressive because of the magnitude of the problems that they solve.Scott Bellware

Microsoft in general has an amazing capacity to state blatantly: “That stuff we sold you last year was total crap but please trust next year’s product.” Read some magazines or books published by Microsofties and you’ll see what I mean. Don Box is playing that same game here: “SOAP was crap. XML Schema was crap. WSDL was crap. But trust us, we know what we’re doing now.” They can’t afford to learn the lesson about premature standardization because they can’t afford to slow the revenue stream (and “thought leadership”) generated by technology churn.Paul Prescod

After using Microsoft products for about seven years, I’m just about burnt out. It was a good ride and it probably made more sense towards the beginning… but it is getting harder and harder to endure each successive turn of the crank.

Stallman: Screw Child Rearing; Contribute to Emacs!

August 13, 2007

That’s one thing about the Open Source movement that’s always troubled me. It’s not just a movement that deals with software and computers, but somehow its followers seem to have been drawn into it for other political, religious, and social reasons. I could never put my finger on what it was that was going on exactly, but I always got the impression that these people “weren’t like me.”

A recent spate of rants sheds some light on to the issues that play into this dynamic. Richard Stallman essentially slams a coworker because his family commitments were going to interfere with the development of Emacs. Now a geek being rude is not a new thing… but the reasoning of geeks coming to the defense of another rude geek can get pretty frightening. Easily the most insightful comment came from Paul Prescod: “If there exists any universal value system that would justify any of the screaming one way or the other in this thread, it surely includes the component that a father has a responsibility to his wife and daughter that takes precedence over his volunteer activities.”

So who is this guy that combines empathy with strong reasoning skills? And more importantly… what language does he program in?? A quick google and I see that Paul Prescod is author of a book on XML and codes in Python. I like his quip that he refuses to become proficient in “indecent” languages. And in spite of his professional accomplishments, he has never forgotten what it was like to be a kid with an 8-bit computer and nothing but a basic manual to go on. He states his dream for the future of programming and computing thusly:

“My dream is a world wherein all but the very lowest levels and tightest loops of programs are written in a language that is so simple that it can be taught in primary school as a first language; where every word-processor user who can write a macro can at least try to dive into their word processor’s source code to fix a bug, because the macro language is also the implementation language.”

But this of course sounds a lot like Small talk. As Mark Miller has noted, “what Smalltalk, and especially Squeak, has achieved that no other system has achieved to date, with the exception of the Lisp machines of old, is a symbolic virtual machine environment that is more relevant to its own use than any other run-time environment out there.”

And of course, this brings us back to Lisp. Pretty much all the arguments against Lisp I can set aside, but I still have one of the “if Lisp is so great” type of worries hanging on. If Lisp is so great… then why don’t we have an operating system written in the language?

My guess as to the answer to that is that its Richard Stallman’s fault. Yeah, C and Unix are the ultimate viruses that propagate against all of our better judgements, but Emacs is just good enough that its not worth the effort. As Dave Roberts says, “having everything integrated, editor, Lisp system, and application, is powerful. While it can’t quite match up to the power of a full Lisp machine, you can begin to realize some of the potential.” Too bad the platform is run by a guy that has little sympathy for average developers that go home at 5PM to assist in child-rearing activities….

Wallingford: SICP not suitable for CS-1

August 9, 2007

SICP may well be the best computer science book ever written, nevertheless Eugene Wallingford believes that it is not suitable as a first course in the subject. He referenced an article in his recent blog post that details some major criticisms of the book:

“SICP doesn’t state how to program and how to manage the design of a program. It leaves these things implicit and implies that students can discover a discipline of design and programming on their own.”

“SICP students must spend a considerable effort on the domain knowledge and often end up confusing domain knowledge and program design knowledge. They may even come to the conclusion that programming is a shallow activity and that what truly matters is an understanding of domain knowledge.”

“Because SICP misses structural recursion and structural reasoning, it confuses implementing objects with object-oriented programming. The book never actually discusses reasoning about, and programming with, classes of data, which is the essence of modern OO programming.”

At the same time, Scheme remains an excellent choice for a first programming language. And functional programming should still be taught before object oriented programming. Meanwhile, street programmers in the real world have the difficulty of learning functional programming AFTER they’ve been trained to think entirely in terms of OOP.

Wallingford mentioned in his post that “a student is motivated to learn when her activities scratch her own itch.” I would say that that’s one of the things that makes learning Lisp difficult. We have to create new itches before we can even want to get started! And worse, you have to set aside some long held assumptions before you can make way for the itches. And finally… it’s just plain work to keep trying to get better. (Some people don’t even make it past the basic Emacs commands….) For people that pride themselves on being smart… it sure is tough working with a language that’s so pure and elegant that you’re limited only by your personal intellectual shortcomings. Normally you’re just limited by the tools you use! Creativity may thrive under artificial constraints, but the same cannot be said for raw power.

Close, but no Cigar: Jasspa MicroEmacs with “It’s All Text!” on Firefox [on Windows]

August 8, 2007

I took half an hour to fiddle with this one.  It sounded promising: use the text editor of your choice to compose text for any type-in box you might find on the web.  (I can’t learn Emacs easily if I keep having to switch back and forth between different text editors all the time.)

The “It’s All Text” plug-in for for Firefox provides a way of eliminating at least a portion of this hassle.  There’s just a couple of problems, though.  Firefox looks crappy on Windows XP compared to the very crisp look I’d just gotten with it on PCLinixOS 2007.  (I’m not sure if I can give up Opera on my Windows boxes yet….)  Jasspa MicroEmacs looks really ugly, by the way, but that’s no big deal; I can just use Emacs 21 or something if I want.  But what really gets me is that the little edit button doesn’t work in the main place that I want it to: the text editing box right here on WordPress for when you’re posting a new entry!  Argh!

Thanks to the anonymous coward that recently posted here (and also to minor Emacs wizardry) for spreading the good news.

(Mozilla’s Outlook-style spell checking feature rocks, though.  The one here on WordPress is an abomination!)


Follow

Get every new post delivered to your Inbox.