Lisp-style Generic Functions in Javascript October 28th, 2013
Patrick Stein

I have been spending some time over at codewars.com. It is an interactive platform where you can train on Javascript, Coffeescript, or Ruby exercises. The other participants in the site add their own exercises.

I just added an exercise to implement Lisp-style Generic Functions (including the standard method combinations) in Javascript. I’m pretty happy with the way my code came out.

var append = defgeneric('append');
append.defmethod('Array,Array', function (a,b) { return a.concat(b); });
append.defmethod('*,Array', function (a,b) { return [a].concat(b); });
append.defmethod('Array,*', function (a,b) { return a.concat([b]); });

append([1,2],[3,4]); // => [1,2,3,4]
append(1,[2,3,4]);   // => [1,2,3,4]
append([1,2,3],4);   // => [1,2,3,4]
append(1,2,3,4);     // => throws "No method found for append with args: number,number,number,number

Here’s a link directly to the exercise, but if you register for the site with this link, I get bonus points.

HTML + JS + LISP. Oh My. March 20th, 2012
Patrick Stein

I started a Javascript + HTML application some time back. I decided that I wanted to get some Lisp on. So, it was time to pull out Hunchentoot, CL-WHO, and Parenscript.

It’s been awkward slogging so far. I still don’t have a good user-model of when exactly I need to wrap something in a (cl-who:str ...) or when Parenscript will expand my macro rather than convert it into a function call or how I managed to get the cl-who:*attribute-quote-char* to finally stick for a few REPLs.

The other half of the awkwardness is that I started writing the application in idiomatic javascript with prototype-based objects.

function MyClass () {
  this.myfirst = undefined;
  this.myarray = [ ];
}

MyClass.prototype.mymethod = function (arg1, arg2) {
  this.myfirst = arg1;
  this.myarray.push(arg2);
};

This makes for some awkward javascript when converted directly into Parenscript because:

  • The method mymethod() will try to return the result of Array.push() (which, technically, is fine, but not really the intent of the method).
  • Almost every statement on the Lisp side ends up wrapping just about everything in (parenscript:chain ...). (Edit: Of course, I discovered right after posting this that the dot is left untouched in the Parenscript symbol conversion, so I can do (this.myarray.push arg2) instead of (parenscript:chain this my array (push arg2)). I’m certainly pleased with the brevity, but it pegs my something’s fishy here, Batman meter.)
  • I have an aversion to using any package other than COMMON-LISP, so everything is way clunkier than all of the tutorials and examples online.

I think that I’m going to scratch all of the Javascript and Parenscript code that I have right now and start over with a mindset of How would I do this if it were just in Lisp? Now, what extra hoops do I need to get Parenscript to make usable Javascript? rather than How would I do this in Javascript? Oh, and then, how can I make Parenscript say exactly that? And, I may bite the bullet and (use-package ...) both CL-WHO and Parenscript.

Blur and Edge Detect your Fourier Transforms September 21st, 2009
Patrick Stein

I have now added convolutions to my FFT Paint application. Here, I started with the following image (again, magnitude on the left and phase on the right):

conv_orig_m  conv_orig_p

From there, I took the Fourier Transform:

conv_pre_m  conv_pre_p

Then, I did a horizontal Sobel operator on it to get this:

conv_post_m  conv_post_p

From there, I did the Inverse Fourier Transform to obtain this:

conv_final_m  conv_final_p

Enjoy!

Simple Function Plotting in Javascript September 15th, 2009
Patrick Stein

graphRather than work more on my FFT Paint program yesterday, I took a break to make a simple function plotter. There are lots of useful Java applets out there that do more than what I’ve done here. And, certainly, gnuplot is much more complete and useful.

On the other hand, if you just want to quickly plot something that you can save as an image, you either have to re-learn gnuplot (every time I use it, I have to sift through the help to figure out how to set up my tics and labels and output size and output filename) or you have to do screen grabs from one of the Java applets.

With the plotter that I wrote yesterday, you click on the Snapshot button, then right-click to save the image or copy it to your clipboard.

Enjoy.

Better Examples of Fourier Transform Painting September 10th, 2009
Patrick Stein

I have now added symmetry options to my Fourier Transform painting application. As PC pointed out in a comment to my previous post, examples with higher frequency information are more interesting. Here are some images of the background tile of this website. The magnitude is on the left and the phase is on the right. You can click them for the full-sized images.

This is the original:

squares_m  squares_p

This is the Fourier transform of the original:

squares_mf  squares_pf

This is my edited version of that transform. I wiped out lots of the off-axis frequencies. I tinted the center red. And, I added some green blotches along the diagonals.

squares_mfe  squares_pfe

And, here is the inverse transform of my edited data.

squares_mfei  squares_pfei

l