vanholes - Van Laarhoven Lenses in Clojure

In two previous posts, I went on about lenses in Clojure. Pinholes comprised a small library of higher order functions to formalize and simplify the viewing and manipulation of complex nested structures. Tinholes did essentially the same thing, but with macros instead. In both cases, there's recursion going on, as we burrow through layers of nesting, but macros had the advantage of doing it all before compilation, giving core.typed a chance to check our work.

The macro post was inexplicably popular, catapulting me to levels of fame I never expected to achieve without consciously emulating an early De Niro …

more ...

tinholes - performant, strongly typed lenses in Clojure

In a previous post, I built up a framework for lens-like constructs in Clojure: essentially some fancified versions of assoc-in and get-in to allow for bidirectional transformations along the nesting path and some utilities to generate special-purpose getter/setter functions. The name, "pinhole," is supposed to suggest a more primitive, utilitarian mechanism for achieving focus.

While still ruing (sort of) other mistakes, I found myself worrying that a triumphal sentence near the end of the piece

What's more, thanks to the expressive power of dynamic Clojure,
and higher order functions, these lenses are not just simple to
use but …
more ...

Pinholes 2 - Ignorance, misrepresentation and prejudice edition

Sseveral comments regarding the pinholes post, have forced me, against the deepest elements of my nature, to engage in thought. Since that might never happen again, I thought it meet to record the event.

I'm going to say "I" a lot, because this is mostly my opinions.

Bidirectional programming

As pointed out by Christian Schuhegger in a comment on the original post, lenses were originally introduced to computer science in the context of bidirectional programming, rather than as a tool for dealing with deeply nested immutable structures. He points to a good list of papers on the subject on the …

more ...

Pinholes - Idiomatic Clojure Lenses

Lenses are a construct for getting, "setting" or "modifying" values within data structures, especially deeply nested data structures. The quotation marks have the usual meaning when they show up in funktionsprache:1 not mutating anything per se, but instead producing an object, or reference thereto, that is identical except for the requested change.

In Scala, the need for lenses is pretty glaring, as illustrated in Eugene Yokota's great explanation of lenses in Scalaz, because of the centrality of case classes. In his example problem, a turtle is represented with three case classes:

  case class Point(x: Double, y: Double …
more ...

'Ducers Wild -- a concise guide to the menagerie

TL;DR

It's not too long, but, to summarize the summary, if you read Rich Hickey's 2014 blog post on transducers first, his 2012 post on reducers will be easier to understand.

Brief Definitions

Herewith, all in one place, are Clojuresque definitions of:

  • reducible
  • reducing function
  • transducer
  • reducer
  • folder
  • decomplected

Longer elaborations of these definitions follow in the subsequent section.

reducing function

Anything that can be used as the first argument of the reduce function, e.g. + or conj. Generally, it's a binary function that returns something of the type of its first argument, which is supposed to be a …

more ...

Testing on Hundreds of AWS Instances - (sort of Distributed functional programming, part 3a)

In part 1 and part2 of this almost unbearably exciting series, I outlined the concept of distributing purely functional programs and went through some implementation details of Girder.

So far, however, I've only asserted that it works, so today I want to start explaining how I used Amazon Web Services to test pretty cheaply on gobs of machines.

The art of AWS wrangling was somewhat new to me, and I went through a few iterations before deciding on the right mix of tools. Needless to say, the right mix ended up being fairly Clojure heavy, which helps to smooth out …

more ...

Distributed purely functional programming, part 2

Update 2015-01-12

The algorithm as it exists in HEAD is somewhat different from the below, in ways that I'll describe (eventually) in an another post. In some ways, it's closer to Fork-Join, but with important differences to support reentrancy, share results of duplicate requests and adjust for the costs of distribution.

Recap of recap

In a previous post, I introduced a framework called Girder (the code is on github), which aims to facilitate Plain Old Functional Programming on distributed systems. By POFP, I mean code that, as much as possible, consists of normal looking calls to normal looking functions, the …

more ...

Quick tip on getting lein to recognize your new dependency

Ever realized you needed to modify some dependency (e.g. I needed to add weak cache support to core.cache), go a head with forking on github, lein install your new version, modify your project.clj to pick it up, and then... somehow... you still seem to get the old version? That's usually because some other dependency is explicitly requesting a version of that library. If you do lein classpath, you'll see your library show up, in two different versions, with the one you don't want first.

In my case, the relevant bit of classpath shows

   /Users/pnf/.m2/repository …
more ...

Beauty and the Beast - Distributed functional programming, part 1

Update 2015-01-12

The algorithm as it exists in HEAD is somewhat different from the below, in ways that I'll describe (eventually) in an another post. In some ways, it's closer to Fork-Join, but with important differences to support reentrancy, share results of duplicate requests and adjust for the costs of distribution.

OSS and Commercial Grids

Grid computing has always suffered the reputation of a buzzword that one suspects might not actually mean anything, but it has become especially ill-defined with the rise of open-source distributed computation frameworks like Spark, Storm and Grampa Hadoop. These extensively documented systems don't need much …

more ...

Yeah, yeah, I should have used perl

Overkill

After reading my compelling post on a clojure Slack-bot, an astute reader1 pointed out that using the fullblown apparatus of compojure, jetty, jvm, etc. for something this silly is really only justified when the entire purpose of the exercise is procrastination. Well, dear astute reader, that was the entire purpose, but you're right. Ok, here it is in perl,

    #!/usr/bin/env perl
    use Mojolicious::Lite;
    use File::Slurp;
    my $token = read_file("TOKEN");
    my @lines = split(/\0/,read_file("LINES"));
    post '/slacks' => sub {
      my $c   = shift;
      my $t   = $c->param('token');
      if ($t eq $token) {
          $c->render(json => {text …
more ...