Friday, July 18, 2008

Fear No Evil II, or Why Solar Power Sucks

Just a quick note cuz I remembered something that answers Dave's well-reasoned comment:

My own personal rule on this is to use functional programming whenever possible and let the GC deal with it. 

Not much of an excerpt, but it says it all: modern Lisp GCs truly Rock the Casbah, and I myself am on record as denouncing the flipside of this blogcoin, consophobia. Actually, there may be a problem, Dave says "whenever" possible and perhaps then we agree! 

But "whenever possible" has a ring to it like "oh, you know, all the time" and I actually had a good reason for not doing that, I just forgot it. Has to do with solar power. 

The reason solar power sucks even though there is an overwhelming amount of it is that it is diffuse. Yes, enough sunlight falls on Kansas in a month (I am making this up) to power Earth for a year, but just try to find a solar panel as big as Kansas, never mind deal with the Kansans or the inefficiency of the transmission to Australia. I digress.

The problem with a "Damn the consing! Full molasses ahead!" policy is that when ones application drags to a halt there will not be a bottleneck to fix. There will just be hundreds of places one was too lazy to think about whether one could use the right construct. And correcting them all will be as painful, tedious, dreary, mind-numbing (sound like fun yet?) and thus as bug prone as it would be easy and fun whenever reaching for a list manipulation tool to challenge oneself with, gee, can I cut in the afterburner? Stand back, GC! Captain Destructo is in da house!

That is a practical objection. My ethical objection (viz, hey, learn the language) is not all that far behind: jeez, I am building this list right here in front of my eyes, why am I not using a destructive operation for the next step? Do these same folks all have a copy-n-sort function in their personal toolkits that begins with a copy-list on the sequence to be sorted? 

No, they do not. Why not? Hello.

My apps periodically get bogged down. I wait until they do and then dive in for what I like to call Speed Week after a regular TV extravaganza on vehicular racing. Normally this turns up interesting algorithmic gaffes I do not feel too bad about but one time the smoking gun was the most innocuous little needlessly copying statement you can imagine write at the center of the heaviest hitter bit of code you can imagine. This is pretty much the opposite of the solar power argument -- there was just one little guy to track down -- but without the code profiler offered by AllegroC I am not sure how long it would have taken to find that. 

And now I come back to the main point: er, exactly how hard is it to know when one can use destructive list operations?  So why not use them? Only one excuse comes to mind (fear) but always copying is not even a clear win (ie, it can totally suck at times) so.... learn the language?

If I was going to cut the Copying Cowards some slack I would say, shucks, not everybody writes insanely intense tight loops. But then I remember a point I made in FNO/1: we get noobs all the time struggling with slow code because of excess copying. Perhaps complex applications and tight loops are orthogonal?

I say learn the damn language.


Dave Roberts said...

Kenny, Kenny, Kenny...

:rolleyes: ;-) ;-)

Okay, I think it's safe to say that you and I probably agree on this. Nobody in their right mind would say "Cons like crazy! It doesn't matter." Nobody in their right mind would say "Absolutely never cons. Ever. Because all that little cons-ing adds up and you'll have a slow program and then Kenny will make fun of you." The reality is always somewhere in between.

I'm actually quite conscious of cons-ing, but I also believe that obsessing about cons-ing leads to premature optimization and far greater numbers of bugs. That does not mean that I always, always, always use functional routines that copy. I'm constantly on the lookout for places where I can eliminate that. But when first writing my program, those places have to be very plain and obvious. Nothing tricky. No corners of the language spec being utilized. If I know I'm building my own list in a function and it's obvious that I own it, fine, I'll PUSH and NREVERSE it all day long. The reason for this is that spending the intense mental cycles to make sure I'm doing it right breaks the flow from the rest of the program I'm writing.

In other words, typically my goal is to get something working as quickly as possible. This helps me mentally for a couple of reasons:

1. I get something working. Yea! Working is always better than not working. I have enough half-finished code littering my hard drive. The more I finish, the better I feel about myself. It's a self-esteem thing. I know you're pretty secure with yourself, so you probably wouldn't understand. ;-)

2. When I do optimization, I really shift mind-sets. I start hunting for problems and issues. It's hard for me to do that at the same time I'm working through the basic algorithms and such. Maybe that's just me, but it really breaks my flow. I appreciate doing things as two distinct steps. And because the system was already running, I can measure what I'm doing as I go along, using TIME to tell me whether I'm actually having an effect on the system or just twiddling my thumbs.

I also agree fully that people should learn the language. But it's safe to say that even language experts will introduce no bugs into the system of the type eliminated by programming functionally when they program functionally. When they program with mutable operations, there is always a chance that they will screw up. Experts will screw up less than noobs, obviously, but there's still a non-zero chance.

In other words, I see many of the non-mutable operations in Lisp through the same lens as I view GC and array bounds checking. All these things help programmers write better code on average. There is a time and a place for manual memory management, too, and a time and place to get rid of all those array bounds checks. But most of the time they provide an overall benefit. Expert C programmers still introduce malloc/free bugs, even though they are experts.

Finally, no matter what you say about me, I'm still going to read your blog. I love you man! ;-)

Anonymous said...

I actually ran into a problem like that, where I overconsed and slowed the app down, because double-floats are always heap allocated in Corman CL. Roger sent me a destructive modification of double floats hack, and I went to work. It didn't take all that long to identify and reduce the consing in some of the heaviest consing places. I would absolutely not worry about consing until it is a problem. After all, it isn't until you put a dogs nose in his pee that he learns to stop, and yet dogs are smart enough to get by....

-Tim Kerchmar

Samuel A. Falvo II said...

PARKING LOTS. ROOFTOPS. These surfaces just suck up solar radiation like a sponge, and contribute to volcanically hot cars and higher air conditioning costs. SOLUTION: Put solar panels there-over or there-on. You don't need *a* solar panel the size of Kansas to harness that kind of energy. You just need to, as you say, "learn the damn language."