Wednesday, April 08, 2009

Twitter/Ruby/Scala/Blah

For some reason I feel compelled to chime in on this debate. I like both languages. I like Scala more, but Ruby is fun.

(Reader Beware: This post was written in one pass with little to no editing.)

I don't like how people get all steamed about their languages, as if it's part of them. But, if used properly, this energy can be channeled into creating better languages, so I guess its a necessary evil. The problem is, it not often used properly. Developers seem to just get mad at each other instead of talking through things civilly, and thinking critically and objectively. This is nothing new, and nothing that hasn't been said a thousand times I'm sure, but I think serves well as a nice introduction.

Maybe the problem is that so many of the elements of programming languages are based on feel, as opposed to simple fact. I wish we'd all think more logically and have nice intelligent debates, and I wish we could support our arguments more with fact.

Now for a debate. I was tweeting with Daniel Spiewak who said,

"Obie has once again decided to completely miss the point. Twitter's legacy code is bad *because* of Ruby, not in spite. The experiences described by @stevej and @al3x precisely mirror my own: it isn't impossible to write large, maintainable Ruby...just hard."

I asked him if he could elaborate on "because of", and to that he replied,

"Ruby makes it *hard* to architect a large infrastructure and to keep it maintainable. I think that dynamic typing is part of the problem, but not all of it. Possibly the way the module system works? It isn't impossible to do large apps in Ruby (as Obie and Ola remind us), but it takes more effort and more discipline. Java and Scala both make this sort of large scale code base much easier to create and maintain."

Now, I don't necessarily disagree with that (and recall that I do like Ruby). But I'd like to point out that I've been on a lot of Java projects that were completely unmaintainable. You could easily call them absolute disasters. In fact, the majority of the Java projects that I've been on have been disasters (yes, yes get your laughs in and tell me that its my fault...but its not. I did a lot to help those failing/flailing projects). Maybe that's because I've picked bad projects, and haven't many changes to work with great teams on applications built correctly from the start.

But, I think that emphasizes my point a little. Who has? How many projects are built correctly from the ground up, by talented, disciplined developers? I'd say not many. Most developers are horrible, and the language wouldn't make a shred of difference. And for those developers who are really good, the language probably doesn't make that much difference either. A group of solid developers could easily build something far more maintainable in Ruby than the garbage developers who are writing in Java.

But can those same developers build something more maintainable in Java or Scala? I think it depends on a whole number of things (listed at the end of the post). If there's a good chance of turnover on the project, then you probably want something with type information in the code because it serves so well as documentation. But if there's little chance of turnover it probably doesn't matter.

That said, even with turnover, because Ruby is inherently higher level that Java its probably more easy to maintain. Java is just not a good language anymore, it has not stood the test of time. It came about to fix some problems with C++, and had a syntax that appealed to those developers, but that was 1994. It has not evolved. Ruby is so much more expressive than Java that the lack of type information probably doesn't mean much at all.

Scala on the other hand, probably no contest for large projects. I think Twitter made the right decision. They get the type safety, the type documentation, and the high level expressiveness all together. I do like Ruby a lot, but Scala just feels better to me, and feel is very important, even if its not measurable.

But all that could be wrong. How many large projects have actually been built in Scala? Few. I said in the beginning that I want people to think critically and objectively. It would be nice if we could base some of these debates on fact. Are there any facts out there that large Java projects are more maintainable than Ruby? There may well be, and if so, we should get that information out there. Then again, there may be documentation that supports the opposite.

So I'm not really calling for comments here, though they are always welcome. What I am calling for is experiments, evidence, observations, or facts that support that one language is more maintainable than the other for any sized project.

Here are some questions whose answers would be helpful (in no particular order):

  • What language was used?

  • What was the size of the project:

    1. LOC? Production and Test code.

    2. Number of developers?

    3. Number of testers?

  • How long did the project take?

  • What was the amount turnover?

  • What was the experience level of the developers?

  • The amount of time the team has been together?

  • The amount of time the developers have spent with the language used?

  • Type of project? (Obviously if the language chosen was a horrible choice for the project, it makes a difference)


This information is probably pretty difficult to come by. The lack of it shouldn't impede intelligent debate, but the presence of it could help us as a community.

Saturday, April 04, 2009

Random Thoughts

I haven't written in a while, but that doesn't mean that a lot hasn't been going on, just nothing I really felt the need to write about unfortunately. I do have some random thoughts about some things though, and so here they are.

Little Things


I've noticed in some of the comments on my posts that people like to point out that some of the things I mention are no big deal - like not having to put a dot in a method call:

p ! t

vs.

p.!(t) or in Ruby: p.! t

I'd like to point out that sure, they are little things. But, little things add up. The more and more of the little things that a language gets right, the more of a joy it is to program in. Scala seems to get a lot of these things right.

Java 7


I remember months ago (at least 4) I asked, "will Java 7 ever come out?" I did a brief google search and see no evidence that its any closer. Why is this? It's insane.

I think the main reason is (so many people have realized and stated this before) that programming language by committee is BS. There must be a dictator running the show. I hope this is a road that Scala doesn't go down.

There are plenty more reasons of course. Holding on for dear life to backwards compatibility is a bad idea IMO. If companies don't want to move forward to a new version because something has changed, then well, you aren't really at risk of losing them as users anyway. If they want to stay on the old version, let them. As a language designer you should not sacrifice the language. You should always do your best to put out the best language possible. If the language is the best, then when the company finally decides to move off the old version, they will move to the latest version. If your language isn't the best, they won't. No big deal.

ScalaTest


I'm finally getting back into ScalaTest development. I'm really excited about it. It's been a while. I'll be giving a presentation at the next Scala meetup on testing in Scala. It won't be specifically to ScalaTest - I'll be including specs, matchers, mocking, ScalaCheck, lots of cool stuff.

Ruby


Ruby is definitely rubbing off on me. I read an interesting quite by Matz that said something along the lines of, "It really comes down to just how you feel writing in a language that matters". I feel good writing Ruby. I feel even better writing Scala (though I do sometimes end up in fights with the type system and get angry). I feel HORRIBLE writing Java.

camelcase vs. underscores


I've decided that camelcase is much harder to read than underscores, and wish the Java and Scala communities would make the switch. WhenIReadCamelCaseAndEverythingIsBunchedUp, its_just_harder_to_read_than_underscores. I think this is especially true as the statement gets longer. TwoWords is not so_bad. ButAfterThat I think underscores_win_out.

Management


I can't begin to explain how good it feels to have good management again. I had a great one a few years back by the name of Eric Golin. He was so incredibly smart and knew how to speak to me and how to get the best out of all times. This is how I feel at my current job. Management has worked extremely hard to get things running smoothly. It just feels great.

I've had so many terrible, terrible, terrible managers in the past - almost all of them. Its an absolute drag. I need to do better to make sure it doesn't happen again.

Here's one tip - if anyone in the management chain wears sunglasses indoors, run like hell.

C++?


I don't have much experience in C++ at all, but, in what little time that I've spent with it, I like it. And I like it a hell of a lot more than Java. Now, I know Java's appeal was that it fixed so many problems C++ developers had to face, but...for the most part I think it just appealed to the 90% of developers who aren't any good.

But, Java probably was a good step back in order to fix some of those problems, in order to allow really nice things like Scala to come along. You know, I used to really like Java, until Scala came along. Now seeing Java code makes me throw up in my mouth a little.

Algorithms


I need to get better at explaining fundamental algorithms. Its not that I don't understand the concepts, I just don't do a good job of explaining my understanding of them. I will improve this.

School


School is a perfect place for me. I have to go back. I change jobs often because I lose interest. I need to be challenged, always. I need new ideas. I need really smart people I can talk to all the time. Very few jobs can offer even half of what I need. I get all these things and more at school.

If I need a challenge, I just pick a challenging class. Almost everyone in my program will be really smart, and interested in exactly the same things as me. Fantastic. And, I wont have to deal with sunglasses indoors.

Wednesday, February 18, 2009

Grad School

I plan on going back to grad school, full time maybe, part time maybe. I want to go for language design, as that's really all I'm interested in, and all I've been concentrating on for the past couple of years (outside of work).

I think the obvious choice is EPFL, but I'm not yet sure what my chances are of getting in. NYU part time is also a good option.

I'm very, very excited about this. In the past two years or so I went nuts and bought probably a dozen language design/compiler books, a dozen math books, and a bunch of books on actual languages. I've clearly been getting ready for this for quite some time, and the time is right.

I need to write my statement of objectives, and if anyone is willing to proofread for me, that would be awesome.

Also, if EPFL doesn't work out, I'd be willing to give some other schools a shot, but only for language design. Anyone out there have any good experiences to share?

NYSE => New York Scala Enthusiasts

Monday, February 23rd, meeting of NYSE, or New York Scala Enthusiasts*. I suspect I'll be presenting regularly, but I won't be presenting at the first meeting - I think someone is speaking about the Actor model this time. My first presentation will likely be about ScalaTest, Specs, and other Scala testing alternatives.

I encourage people who actually care about programming to join us, and programmers who don't care about programming to fall off the GW bridge.

* (Very funny that its called NYSE, given my very infamous stay with the actual company, and how that sham of a technology company wouldn't accept Scala at all, despite my best efforts. Anyway, looks like there will finally be a NYSE in town that embraces Scala.)

Wednesday, January 28, 2009

Deeper Look at the Apply Method in Scala

In Scala, there is a language feature generally referred to as "The Apply Method" that has the following rules:


  1. Any object that has an apply method can be called with the .apply omitted.
  2. Functions are no more than objects.


Let's take a look at an example. Given the following abbreviated definition of class Array, and an instance a,

class Array{
def get(index:Int) = { ...some code to get from the array... }
def apply(index:Int) = get(index)
}

val a = new Array(whatever)

Then the following calls are essentially equivalent:

a.apply(7)
a(7)
and also:

a.get(7)

(the call to get is only equivalent because apply simply calls get. apply could have any implementation, of course.)

While apply is really useful in cleaning up syntax, the real beauty of it is hidden just below the surface. (Note: Some of the following might not be implemented exactly as I describe, I'm not 100% sure, but for the sake of understanding, I think it's okay.)

Scala'a apply is a concept that can be considered universally across functions or methods, objects, anonymous functions, case classes, and the like. In Scala, a method is nothing more than a Function object containing an apply method which takes the same arguments as the method itself.

Let's take a look at a more in depth example. All three of the following are basically equivalent:
  
def shout1( word: String ) = println(word + "!")

val shout2 = new Function1[String, Unit] {
def apply(word: String) = println(word + "!")
}

val shout3 = (word:String) => println(word + "!")

All three are of type Function1[String,Unit], which has an apply method that takes a String and returns Unit. Notice that shout3 uses anonymous function syntax. This is really nothing more than syntactic sugar for Function1. All three can be called like so:

shout1("hey")
shout2("hey")
shout3("hey")

The following client code further demonstrates that they all derive from the same type.

def ohYeah( f: String => Unit ){
f.apply("oh yeah")
f apply "oh yeah"
f("oh yeah")
}

ohYeah(shout1)
ohYeah(shout2)
ohYeah(shout3)

However, one thing I find odd that cannot be done is the following:

shout1.apply("hey") // compiler error!
shout2.apply("hey") // ok
shout3.apply("hey") // ok

If anyone smarter than me cares to chime in on that one, I'd be quite happy. Apparently Scala doesn't always treat actual methods exactly the same as the equivalent Function values, but I'm not sure why. I tend to think it should. There must be a good reason.

The first rule applies to top level objects, functions, and objects defining apply, but what about classes? Are classes no more than objects in the language, the same way that functions are?

Unfortunately, it appears the answer is No.

Before we get into that, let's that a quick look at the exception to that - case classes. For any case class C, you can say C(), and that returns you an instance of that class. Hmm... C(). That looks an awful lot like what we've been looking at. As it turns out, it is.

In Scala, when you define a case class, a corresponding top level object with the same name is created. This object is a factory which creates objects of the original class. It contains an apply method that takes the same arguments as the constructor of the original class and simply calls that constructor.

A quick example should help:

case class Dood(name: String)

class DoodClient {
val a = new Dood("Jack")
val b = Dood("Daniels")
val c = Dood.apply("Cough")
}

The expressions in b and c are equivalent. b is just shorthand for c. In both lines, Dood refers to the top level object Dood, and not the class.

Knowing all this, I should correct myself. I said case classes are an exception to the rule that classes aren't simply objects in the language. This isn't really true. Creating the case class Dood creates both a class and a top level object. It's that object that has the apply, and the class itself still isn't a full fledged object.

But why? Well, I think the short answer is that on the JVM classes aren't top level objects. That seems like a cop out answer though. Let me explore it for a bit, though I'm really just thinking out loud.

If they were top level objects containing an apply method then we could probably do away with the new keyword entirely, and then any call to any object would simply be a call to apply. Things would be entirely consistent both from the internal language representation, and from the perspective of the developer as well.

But what are the consequences of this? I guess I'm not sure. I'm going to have to think through it a bit harder. I'd appreciate comments from anyone with more knowledge on the subject than myself.

Monday, January 26, 2009

Maven: WTF

I'm on the train, trying to do a build, and this happens:

[INFO] ------------------------------------------------------------------------
[INFO] Building myProject
[INFO] task-segment: [clean]
[INFO] ------------------------------------------------------------------------
[INFO] artifact org.scala-tools:maven-scala-plugin: checking for updates from scala-tools.org
[WARNING] repository metadata for: 'artifact org.scala-tools:maven-scala-plugin' could not be retrieved from repository: scala-tools.org due to an error: Error transferring file
[INFO] Repository 'scala-tools.org' will be blacklisted


WTF?

Because I'm not online maven totally explodes and threatens to blacklist stuff?

I'm sure this is 'configurable' or whatever...but wtf, this just shouldn't happen. Since I wasn't online, I couldn't easily lookup what to do, so I couldn't build at all. Thanks Maven.

I'm thoroughly annoyed.

Sunday, December 28, 2008

More On My Scala Query DSL

I know I promised to explain some things that I still haven't explained, but unfortunately I won't be doing that just yet. I've been too busy coding. I made some cool additions to what I do have though. Now, I can query over more things that just a dictionary of words. In this post I'll show some examples using music scales. Additionally, I added orderBy, and limit stuff, which was really fun.

I've added google code project for this as well, because I kept adding stuff to my cpusimulator project, and it clearly didn't belong. Here's the link: dslplayground.

Here's some examples:


1 val c_maj_and_a_min = contains(Chord("C", Maj), Chord("A", Min))
2
3 var scales_desc =
Scale find(c_maj_and_a_min) limit 4 orderBy (rootChord, Desc)
4 var scales_asc =
Scale find(c_maj_and_a_min) orderBy (rootChord, Asc) limit 3
5
6 scales_desc foreach println
7 println("-------------------------")
8 scales_asc foreach println

Here I'm searching for all Scales (just major and minor scales) that contain Cmaj, and Amin.

On line 3 I'm limiting my search to 4 scales, and ordering the results by the rootChord of the scale, descending.

On line 4 I'm limiting my search to 3 scales, and ordering the results by the rootChord of the scale, ascending. But, notice I've done this in the opposite order as line 3. (The behavior changes though, if I limit the unordered result set before I order it, or after...not sure what to think about that.)

Lines 6,7, and 8 yield:

List(Chord(G,Maj), Chord(A,Min), Chord(B,Min), Chord(C,Maj), Chord(D,Maj), Chord(E,Min), Chord(F#,Dim))
List(Chord(F,Maj), Chord(G,Min), Chord(A,Min), Chord(Bb,Maj), Chord(C,Maj), Chord(D,Min), Chord(E,Dim))
List(Chord(D,Min), Chord(E,Dim), Chord(F,Maj), Chord(G,Min), Chord(A,Min), Chord(Bb,Maj), Chord(C,Maj))
List(Chord(C,Maj), Chord(D,Min), Chord(E,Min), Chord(F,Maj), Chord(G,Maj), Chord(A,Min), Chord(B,Dim))
-------------------------
List(Chord(A,Min), Chord(B,Dim), Chord(C,Maj), Chord(D,Min), Chord(E,Min), Chord(F,Maj), Chord(G,Maj))
List(Chord(C,Maj), Chord(D,Min), Chord(E,Min), Chord(F,Maj), Chord(G,Maj), Chord(A,Min), Chord(B,Dim))
List(Chord(D,Min), Chord(E,Dim), Chord(F,Maj), Chord(G,Min), Chord(A,Min), Chord(Bb,Maj), Chord(C,Maj))


The fantastic thing about all this is the implementation. I've genericized the stuff I did with Scrabble in a really clean way, and to add search support for an already existing Scale library all I had to do was:


object Scale extends Search[Scale]{
def all = notes.map(MajorScale(_)) ::: notes.map(MinorScale(_))
def rootChord( s: Scale ) = s.rootChord
}

object ScaleMatchers {
def contains(chords: Chord*) = (s: Scale) => {
chords.foldLeft(true){ (b,c) => b && (s contains c) }
}
}

By extending the Search trait, I get all sorts of nice ability to search. All I need to do is provide the definition of the all function. Then, I just define some matchers (in this case only one), and I'm all set to start searching through my data.

Hopefully I'll be able to extract out some of the common matcher stuff as well. I don't think this will be all that difficult.

Its important to note a choice that I've made here. I'm forcing the definition of the all method. Basically, right now, every search loads all the data, and then works on it. Certainly this won't scale, but, this is just a simple little DSL. The underlying implementation could be optimized later. Doug Lea taught me that that is the way you should design languages. First, work on getting the language correct, then worry about performance.

Monday, December 22, 2008

Fun DSL Query Language for Scala

(Quick Note: If you just want to skip to the code, it's interspersed throughout the post. But, for your convenience, I've also put it all in one place at the bottom of the post.)

I've done it! Sick as a dog yesterday, I refactored the crap out of my Scrabble stuff, to create a really powerful query DSL. The kicker? It's only 24 lines of code! It allows you to do all sorts of crazily powerful queries. Lets take a look. I'm so excited! I can't stop typing exclamation points! I actually think this is the best code I've ever written. 1

I'd love to talk about the code smells of my last post, and how I ended up where I did, but to be honest, the code seems so much different now that it would be difficult. I'll just dive in.

Once again I'll start with the test code, which models the original requirements. Don't worry if you don't understand how it works just yet, because I'll explain later. For this first bit, I'm just going to try to explain what it does.

val dictionary = new Dictionary(getWords())
val tray = "defilnr"

// the 4 original requirements
val all = dictionary find includes_all(tray)
val any = dictionary find includes_any(tray)
val only = dictionary find includes_only(tray)
val all_and_only =
dictionary find (includes_all(tray) and includes_only(tray))

print(all, only, all_and_only)

Let me sum up what's going on here.
  • With "all", I've filtered the dictionary to find words that include all the letters in my tray. This produces a small list of very long words - something like: List(adenoliomyofibroma, antifederal, antifederalism, antifederalist, ... )
  • Similarly with "any", I've filtered the dictionary to find words that include any of the letters in my tray. This produces a gigantic list that I won't even begin to list here.
  • With "only", I've filtered the dictionary to find words that include only of the letters in my tray. This produces
  • a very large list - something like: List(d, d, de, dee, deed, deedeed, deer, defend, defender, defer, ... )
  • Finally, the important query, with "all_and_only", filtered the dictionary to find words that include words that include all the letters in my tray, and only the letters in my tray, just as the code reads. This produces something much more helpful to me in Scrabble: List(flinder, infielder)

A key thing to notice is the "and" on this line:

dictionary.filter(includes_all(tray) and includes_only(tray))

But like I said, I'll explain the hows later. Now I'll introduce a couple of new concepts with this line of code:

val all_or_min_10 = dictionary(includes_all(tray) or max_length(7))

The two new concepts on this line are:
  • "or", which is very similar to "and" and very self explanatory.
  • Notice I'm not calling dictionary "find" some_criteria, I'm just calling dictionary(some_criteria). I'll explain how this works later as well. I'm not actually sure I like it, but I figured I'd give it a shot to see how the code looks.

Time for more:

val xin_or_max_4 =
dictionary search (starts_with("xin") or max_length(4))
val van_or_min_4 =
dictionary search (ends_with("van") and min_length(4))

Some more new concepts on these lines are:
  • The "search" method is also an alias for find. But, the actual aliasing is pretty neat, so it will be cool to show how later.
  • Several new criteria functions - starts_with, ends_with, max_length, min_length, which I think are also very self explanatory in what they do.

If I'm moving quickly its because I'm really excited to get into the next part, where I build up a much more complex query.

Complex Queries


val complex_query =
(
(starts_with("d") and ends_with("ing")) or
(starts_with("b") and ends_with("ed"))
) and max_length(7) and min_length(4)

var result = dictionary find complex_query
print(result)

Yes! This seems to have really put it all together. In this query I'm asking for words that start with 'd' and end with 'ing', OR words that start with 'b' and end with 'ed', and any words found must have a maximum length of 7 and a minimum length of 4. I build up the query first, and then ask the dictionary to execute it for me. This seemingly innocent feature plays an important role in abstraction. Which hopefully we'll get to see in just a bit.

Executing this query gives me something like: List(babied, backed, bagged, baked, balled, banded, bangled, banked, barbed, barred, ... dueling, duffing, dumping, during, dusting, dyeing, dying)

Adding onto existing queries


But, I'm not satisfied with my results. Maybe I can't seen to find a place on the Scrabble board where an "a" can be used, and I don't have one in my tray. I want to re-execute my query, but remove all the a's. Here's how:

val complex_query_without_a = complex_query and includes_none("a")
result = dictionary find complex_query_without_a
print(result)

Fancy Schmancy! Executing this query gives me: List(bebed, bebled, bedded, beedged, beetled, beeweed, beinked, beliked, ... dueling, duffing, dumping, during, dusting, dyeing, dying)

Language Features


Before we go into the hows, lets take a very, very quick theory break. Taken straight from SICP, any language gives you three things:
  1. Primitive Expressions
  2. A means of combination
  3. A means of abstraction

Does this little DSL cover those criteria? Yes (though point 3 is somewhat shaky). Anyway, as we cover the hows, we'll refer back to those points to demonstrate how this DSL fulfills them.

Primitive Expressions


We're finally to the implementation (though I suppose many of you probably just scrolled down).

The query criteria methods are basically our primitive expressions in this DSL. 2 Here is the list of primitives provided, and their implementations. I suspect that other primitives will be added soon.

1 object WordMatchers{
2 def includes_only(s: String) = (t: String) =>
inverse(s).foldLeft(true)((b,c) => b && (! (t contains c)))
3 def includes_none(s: String) = (t: String) =>
s.foldLeft(true)((b,c) => b && (! (t contains c)))
4 def includes_all(s: String) = (t: String) =>
s.foldLeft(true)((b,c) => b && (t contains c))
5 def includes_any(s: String) = (t: String) =>
s.foldLeft(false)((b,c) => b || (t contains c))
6 def starts_with(s: String) = (t: String) => t startsWith s
7 def ends_with(s: String) = (t: String) => t endsWith s
8 def max_length(max: Int) = (s: String) => s.trim.length <= max
9 def min_length(min: Int) = (s: String) => s.trim.length >= min
10 def inverse( s: String ) =
"abcdefghijklmnopqrstuvwxyz".filter(!s.contains(_) )
11 }

Ok...I hope no one kills me when I say I'm going to save the how for this one for the next post. That's the implementation. It's pretty crazy, and can probably only be read by pretty experienced developers. I'm really tired and still not feeling great, so I'm going to wait so I don't mess it up.

Means of Combination


The means of combination in this DSL are very simple (at least from a users standpoint). They are simply and and or.

The implementation of those combinations are pretty complex though.

1 object Criteria{
2 implicit def funcToCriteria[T](f: Function1[T, Boolean]) =
new Criteria(f)
3 }
4 class Criteria[T](val f: Function1[T, Boolean]) {
5 def apply(t: T) = f(t)
6 def && (c: Criteria[T]): Criteria[T] = (t: T) => f(t) && c.f(t)
7 def || (c: Criteria[T]): Criteria[T] = (t: T) => f(t) || c.f(t)
8 }

Criteria is some seriously powerful magic, and is totally awesome. I'm also going to wait, and explain both the primitives, and combinations in the next post, which will probably be just tomorrow night. Maybe I'll just update it right here. Maybe I shouldn't even post this yet until I'm finished, but I know there are people that read my blog and this is too cool to wait on!

Execution


Before we take a look at our means of abstraction, lets take a quick look at the Dictionary class, which is something like the DSL's runtime environment, and VM. It holds the words (the environment), and executes the queries which search over those words (VM).

1 case class Dictionary( words: List[String] ) {
2 def apply(criteria: Criteria[String]) = words.filter(criteria(_))
3 def find = apply _; def filter = apply _; def search = apply _;
4 }

Its fairly simple, simply asking the Criteria to evaluate themselves, for each word in the dictionary. If the word doesn't fit the criteria, it is filtered out.

One thing that I really wanted to get to (which doesn't have a whole lot of importance, but is really cool) is the method aliasing. Check out line 3. I've aliased find, filter, and search all to apply, so that a user can call any of them. Maybe that's confusing and not needed, but it was fun.

Means of Abstraction


This DSL borrows its means of abstraction from the Scala language itself, but so far does a pretty poor job of it.

Let's revisit the very last example:

val complex_query_without_a = complex_query and includes_none("a")
result = dictionary find complex_query_without_a
print(result)

I intentionally left out the declaration of complex_query. Do you remember what it does? I suspect not. I could tell you that its a query "asking for words that start with 'd' and end with 'ing', OR words that start with 'b' and end with 'ed', and any words found must have a maximum length of 7 and a minimum length of 4. But, I shouldn't have to. Somehow the code should provide that information upon reading it. There are ways we could do this, but they aren't great, in my opinion.

We could say:

val starts_with_d_and_ends_with_ing_OR_starts_with_b_and_on_and_on_and_on =
(
(starts_with("d") and ends_with("ing")) or
(starts_with("b") and ends_with("ed"))
) and max_length(7) and min_length(4)

But, that really doesn't work. I mean, not only does the variable name go right off the stinkin' page, but the entire implementation is encoded into it. I think that its possible that this DSL fails at doing a great job of abstraction because the underlying nature of the thing its trying to represent - queries matching specific criteria - doesn't really lend itself to abstraction very well. If anyone has any ideas on how this could be improved, I'd be grateful.

OK....that's all for now. I know this thing sort of deteriorated at the end as I got tired, but I'll fix it up really soon. Hope you love it!

Implementation


As promised, here's all the code in one place:

package com.joshcough.scrabble

import Criteria._
import Dictionary._
import WordMatchers._
import org.testng.annotations.Test
import scala.io.Source

class ScrabbleTest {

val lines = Source.fromFile("/usr/share/dict/words").getLines
val words = lines.toList.map(_.trim.toLowerCase)
val dictionary = Dictionary(words)

@Test def tests {

val tray = "defilnr"

// the 4 original requirements
val all = dictionary find includes_all(tray)
val any = dictionary find includes_any(tray)
val only = dictionary find includes_only(tray)
val all_and_only = dictionary find
(includes_all(tray) and includes_only(tray))
print(all, only, all_and_only)



// additional cool things
// (use of Dictionary.apply and Criteria's "||" method )
val all_max_7 =
dictionary(includes_all(tray) and max_length(7))
val all_or_min_10 =
dictionary(includes_all(tray) or max_length(7))
print(all_max_7, all_or_min_10)



// more things (use of Dictionary.filter,
// starts_with, ends_with, max_length, min_length)
val xin_or_max_4 =
dictionary search (starts_with("xin") or max_length(4))
val van_or_min_4 =
dictionary search (ends_with("van") and min_length(4))
print(xin_or_max_4, max_4_or_van)



// more complex query
val complexQuery =
(
(starts_with("d") and ends_with("ing")) or
(starts_with("b") and ends_with("ed"))
) and max_length(7) and min_length(4)

var result = dictionary find complexQuery
print(result)



// hmmm, but i didnt like my result...
// how about i modify my query...
val complexQueryWithoutAs = complexQuery and includes_none("a")
result = dictionary find complexQueryWithoutAs
print(result)
}

def print[T](lists: List[T]*) = lists foreach println
}

/**
* @author dood
* Date: Dec 21, 2008
* Time: 10:09:24 PM
*/
object Criteria{
implicit def funcToCriteria[T](f: Function1[T, Boolean]) =
new Criteria(f)
}

class Criteria[T](val f: Function1[T, Boolean]) {
def apply(t: T) = f(t)
def and (c: Criteria[T]): Criteria[T] = (t: T) => f(t) && c.f(t)
def or (c: Criteria[T]): Criteria[T] = (t: T) => f(t) || c.f(t)
}

/**
* @author dood
* Date: Dec 21, 2008
* Time: 11:24:22 AM
*/
case class Dictionary( words: List[String] ) {
def apply(criteria: Criteria[String]) = words.filter(criteria(_))
def find = apply _; def filter = apply _; def search = apply _;
}

/**
* @author dood
* Date: Dec 22, 2008
* Time: 3:12:35 PM
*/
object WordMatchers{
def includes_only(s: String) = (t: String) =>
inverse(s).foldLeft(true)((b,c) => b && (! (t contains c)))
def includes_none(s: String) = (t: String) =>
s.foldLeft(true)((b,c) => b && (! (t contains c)))
def includes_all(s: String) = (t: String) =>
s.foldLeft(true)((b,c) => b && (t contains c))
def includes_any(s: String) = (t: String) =>
s.foldLeft(false)((b,c) => b || (t contains c))
def starts_with(s: String) = (t: String) => t startsWith s
def ends_with(s: String) = (t: String) => t endsWith s
def max_length(max: Int) = (s: String) => s.trim.length <= max
def min_length(min: Int) = (s: String) => s.trim.length >= min
def inverse( s: String ) =
"abcdefghijklmnopqrstuvwxyz".filter(! s.contains(_) )
}


(1) - I hate the NYSE for keeping me in an intellectual prison for so long, and hate myself for not leaving sooner.

(2) - However, this is an internal DSL, and so you are free to build up more and more primitives, which makes them seem not really like primitives at all...

Sunday, December 21, 2008

Using Scala First Class Functions By Name

WARNING: Today I changed this code all around, and I'll be reposting it soon. This post is still cool, and nothing is wrong with it, but, now the code is wicked awesome!!! So, look for it to be refreshed soon!

It occurred to me that while I knew really well how to pass anonymous functions around in Scala, I had very little experience passing around functions by name. I'm not sure why this is, but I think there isn't all that much out there written about it. It's important to understand that anywhere you could use an anonymous function, you could also use an existing function. Passing functions by name really helps clarify the intent of your code, and for DSL's in general. I'm going to try to demonstrate how to do so, for those who might be in the same boat as me.

I wrote a little app that searches through /usr/dict/words to find words matching the letters that I have in my Scrabble tray. Yes, I could have easily done this with "cat /usr/dict/words | grep someRegEx", but, the point was to learn more about functions.

(quick note...this post is really really long, but i think its full of good information)

First, I needed to be able to determine the following information about a word:
  • Does the word contain ALL the letters in my tray? (but maybe some other letters)
  • Does the word contain ONLY the letters in my tray? (no other letters allowed)
  • Does the word contain ANY of the letters in my tray?
  • Does the word contain NONE of the letters in my tray?
  • Lastly, does the word contain ALL of the letters in my tray, and ONLY the letters in my tray?

To do this I added a function to String that takes the characters to search for, and then any number of additional criteria. The criteria are functions that I reference by name. Lets see the client code, then I'll explain in more detail. Bear with me, I know its frustrating not seeing the actual library code, but I do think it helps to understand how its used before reading it.

1 class StringSearchTest {
2
3 import org.testng.annotations.Test
4 import PimpedString._
5 import Equalizer._
6
7 @Test
8 def testSearch {
9 var word = "ketoid"
10 word.searchFor("ke", word.includes_all) mustBe true
11 word.searchFor("ke", word.includes_none) mustBe false
12 word.searchFor("xzy", word.includes_none) mustBe true
13 word.searchFor("ke", word.includes_only) mustBe false
14
15 word = "keyyek"
16 word.searchFor("key", word.includes_only) mustBe true
17 word.searchFor("xyz", word.includes_any) mustBe true
18 word.searchFor("abc", word.includes_any) mustBe false
19 word.searchFor("key", word.includes_only, word.includes_all) mustBe true
20 word.searchFor("key", word.includes_all, word.includes_none) mustBe false
21 }
22}

Let's break down line a few lines:

10 word.searchFor("ke", word.includes_all) mustBe true
  • "word" is the word we are searching.
  • "ke" is what we are searching for.
  • "word.includes_all" is the criteria. This particular criteria states that 'word' must include all the letters we are searching for. In this case, word must contain both k and e.
  • The statement itself (word.searchFor("ke", word.includes_all)) returns a Boolean. True if the word matches the search criteria, false otherwise.

11 word.searchFor("ke", word.includes_none) mustBe false
12 word.searchFor("xzy", word.includes_none) mustBe true

includes_none is very much the opposite of includes all. It ensures that the word contains NONE of the things we are looking for. The statement in line 11 evaluates to false because the word does contain k (and e for that matter). Line 12 evaluates to true because they word does not contain x, y, or z.

16 word.searchFor("key", word.includes_only) mustBe true

This is nearly the same as the line 10, but the criteria is more restrictive. includes_only states that the word must include only letters that we are searching for. If we were searching for "key" in the word "hey", this would fail, because our word contains an "h".

17 word.searchFor("xyz", word.includes_any) mustBe true

Also very similar to above, but includes_any evaluates to true if the word contains ANY of the things we are searching for.

20 word.searchFor("key", word.includes_only, word.includes_all) mustBe true

Finally the moment of truth, line 20 is the most important of all. It states that the word must contain ONLY the letters in my tray, and ALL of the letters in my tray. This is the easiest way to find Bingo words. (It doesn't yet work perfectly, if my tray contained "key" and the word was "keyyyy", it would still evaluate to true. I need to fix this.)

Finally, before we see the actual library code, lets take a second to understand what "word.includes_all" actually is. "word.includes_all" is a higher order function that takes an Array of Char, and returns a function that takes a Char and returns a Boolean. A higher order function is a function that takes a function as an argument, returns a function, or both. includes_all does both. Higher order functions have been explained by everyone and their brother since 1960, so I won't be doing that here. I'm just explaining how to pass functions by name.

Ok, lets take a look at the library code and I'll explain in more detail.

1 object PimpedString {
2 implicit def pimpMyString(s: String): PimpedString =
3 new PimpedString(s)
4 implicit def convertToCharArray(s: String): Array[Char] =
5 s.toCharArray
6 }
7
8 class PimpedString(s: String) {
9
10 def includes_all(chars: Array[Char]) =
11 fold(chars)(s contains _)
12 def includes_none(chars: Array[Char]) =
13 fold(chars)(!s.contains(_))
14 def includes_any(chars: Array[Char]) =
15 chars.foldLeft(false)((b,c) => b || (s contains c))
16 def includes_only(chars: Array[Char]) =
17 includes_none(inverse(chars))
18
19 private val letters = "abcdefghijklmnopqrstuvwxyz".toCharArray
20 private def fold(chars: Array[Char])(f: Char => Boolean) =
21 chars.foldLeft(true)(_ && f(_))
22 private def inverse( chars: Array[Char] ) =
23 letters.filter(! chars.contains(_))
24 def searchFor(chars: Array[Char],
25 criteria: Function1[Array[Char], Boolean]*): Boolean = {
26 criteria.foldLeft(true){(b, f) => b && f(chars)}
27 }
28 }

(quick note: I've written about implicits here, and here, and I've written about foldLeft here, and I won't be covering them in any detail here.)

Let's just skip right ahead to line 10:

10 def includes_all(chars: Array[Char]) = fold(chars)(s contains _)

As advertised, includes_all is a higher order function that takes an Array of Char, and returns a function that takes a Char and returns a Boolean. Let's take a look back at the original code to see how it was used:

10 word.searchFor("ke", word.includes_all) mustBe true

Now, I could have just used an anonymous function here for my criteria. Assuming that the fold method wasn't private, it would look like this:

10 word.searchFor("ke", word.fold(chars)(s contains _)) mustBe true

The call to fold is basically saying look at each of the search characters and make sure I contain it. fold also returns a function that is executed in search. I could do this, but since includes_all is so common, so reusable, that instead of passing it anonymously, I give it a name, and reuse it all over. And, giving it a name makes it much, much more clear as to what is going on. The second version of line 10 is almost indecipherable.

That basically sums up how to reference functions by name, and pass them around. I'm going to finish the post, showing the actual Scrabble code. However, I don't think there are any ideas that I haven't already covered. Let's start by reviewing the original requirements, since its been a while:

Find all possible words where:
  • The word contains ALL the letters in my tray. (but maybe some other letters)
  • The word contains ONLY the letters in my tray. (no other letters allowed)
  • The word contain ANY of the letters in my tray. (other letters allowed)
  • The word contains ALL of the letters in my tray, and ONLY the letters in my tray.

Now to be consistent, lets look at the test/client code, because that's where you should always start.

1 object ScrabbleTest extends Application{
2 val tray = System.getProperty("tray").toString
3 val scrabble = Scrabble(tray)
4
5 println(scrabble.find(scrabble.all_letters_in_tray))
6 println(scrabble.find(scrabble.only_letters_in_tray))
7 println(scrabble.find(scrabble.any_letters_in_tray))
8 println(scrabble.find(
9 scrabble.only_letters_in_tray,
10 scrabble.all_letters_in_tray))
11 }

I think I have to take some pride in this. The code reads very, very close to the actual requirements. So much that I'm not going to explain it, except to point out again that scrabble.all_letters_in_tray is another example of passing a function by name.

Let's just go right to the library code.

1 case class Scrabble(tray: Array[Char]) {
2 val lines = Source.fromFile("/usr/share/dict/words").getLines
3 val words = lines.toList.map( _.toLowerCase )
4
5 def only_letters_in_tray(s: String): Function1[Array[Char], Boolean] =
6 s.includes_only
7 def all_letters_in_tray(s: String): Function1[Array[Char], Boolean] =
8 s.includes_all
9 def any_letters_in_tray(s: String): Function1[Array[Char], Boolean] =
10 s.includes_any
11
12 def find(criteria: Function1[String, Function1[Array[Char], Boolean]]*) = {
13 words.filter( word => {
14 word.searchFor(tray, criteria.map( _(word) ):_* )
15 }).map(_.trim)
16 }
17 }

Scrabble defines its own criteria functions - only_letters_in_tray, all_letters_in_tray, and any_letters_in_tray. But they are essentially just wrappers around the String criteria functions. This is a testament to how nice and reusable those original functions were, and why I luck out and don't have to explain them :)

The find here simply takes N criteria, and passes wrapped functions onto the String searchFor method. Line 14 is pretty insane, especially criteria.map( _(word) ):_*. It certainly takes some experience before being able to read (or write that line). Fortunately, as a user, the code is absurdly simple, so it doesn't really matter.

That's all for now. I hope this helped.

Anyone want to play me in Scrabble?

Saturday, December 20, 2008

Ruby over Scala

As promised, here is where I'll be maintaining the things I like about Ruby better than Scala. In general, I do think I prefer programming in Scala, but certainly some of the things I can do in Ruby are much easier. If you're looking the other post, its here: Scala over Ruby.

This list is my no means complete and as with the other list, I'll be appending to it here as I learn more.

Pimp My Library


I'll dive into some general theory about this first, but for those who just want to see the code, just scroll down.

There's been so many times when I've needed to add methods to classes, for good reasons. Well, I suppose I didn't "need" to, but the main good reason of course is readability. Having your data and operations on that data in one place is nice. Calling those operations consistently is very important.

Let's use an example in Scala. I couldn't find a "compact" method on List. It like seems it should be there. It's certainly useful. I could just create a method called compact, which takes a List, like so:

def compact[T]( list: List[T] ) = l.filter( _ != null )

But as I just said, calling operations on your data consistently is important for readability. Having this method forces me to call my operations differently. It's confusing calling some methods as infix, and some as prefix. Sometimes I say myList.whatever, and other times I say whatever(myList). The situation is even worse if that method takes arguments. myList.whatever(x), or whatever(myList, x). Inconsistent, confusing, ugly.

One solution is to simply add that method to the class you're operating on. Scala and Ruby both provide mechanisms for doing so, but they differ greatly. In Scala, I have to provide an implicit conversion from the class I'm operating on to a class that has a the method that I want to call. Here is the code:

class Compactable[T](l: List[T]){
def compact = l.filter( _ != null )
}

implicit def compactableList[T]( l: List[T] ) = new Compactable(l)

val list = List( 1, null, 2, null, 3, null )

println(list) // prints all values including the nulls
println(l.compact) // prints just the values 1, 2, and 3

This isn't terrible, but it really clouds my actual intent: I just want to add a compact method to List. Why should I have to convert it to something else, only to have the compiler figure out what I really wanted? While there are some other great uses for implicit conversions, in this particular case something that should be very simple has been made overly complex. Maybe there is a better way of doing this in Scala but I haven't seen it. In addition, I've seen this pattern so many times in Scala code written by other people, so I don't think there is a different way. This code is really just boilerplate.

In Ruby things are much more straight forward.

module Enumerable
def collect_with_index
idx = -1
collect{|elm| idx = idx + 1; yield(idx, elm)}
end
end

(Note: I've used a different method because the compact method already exists. I couldn't find a collect_with_index method.)

Here, I essentially just open up Enumerable and add the method to it. Done. The intent is preserved. Everything is clear, and simple. So simple in fact, that I don't even think I need to explain it.

I could imagine something very similar existing in Scala.

extend trait List[T]{
def compact = filter( _ != null )
}

This doesn't violate encapsulation because I'm not accessing any internals of List that aren't available to me otherwise. This could just be syntactic sugar for the Scala code above. Maybe someday.

Also, I think C# has similar mechanisms, but I'm admitting my inexperience. I'd love to see replies on how this is done in other languages.

Classes are Objects


In Scala, and Java, classes aren't really objects, at least the way they should be. Ruby (and I'm sure Smalltalk, and other languages) gets this right.

I had a discussion with my friend the other day and he asked, "what do you mean? I can call getClass on an object, and call methods on that class...". Eh, you can, but its still a weird fabrication. To a Rubyist, its laughable. So, without further ado, here's an example for Java programmers (in Java because Scala doesn't have static methods)

Let's say I have a simple little interface for a factory that creates Connection objects, and an implementation.

interface ConnectionFactory{
Connection createConnection( String user, String pass );
}

class ConnectionFactoryImpl implements ConnectionFactory{
Connection createConnection( String user, String pass ){
return new WhateverConnection( user, pass );
}
}

Then I have a client that uses a ConnectionFactory:

class ConnectionFactoryClient{

ConnectionFactory factory;

ConnectionFactoryClient( ConnectionFactory factory ){
this.factory = factory;
}

void doIt(){
Connection c = factory.createConnection( "dood", "secret" );
c.connect();
}
}

Now, imagine I had a class that had createConnection as a static method like so:

class ConnectionFactoryClass{
static Connection createConnection( String user, String pass ){
return new OtherConnection( user, pass )
}
}

You can see that the class itself seems like an object that implements the ConnectionFactory interface. If classes were really first class objects, and the class objects themselves could implement interfaces, then I could pass this class into the client like so:

new ConnectionFactoryClient( ConnectionFactoryClass )

You can do this easily in Ruby. This is because classes in Ruby are objects that respond to messages. They aren't really much different than the instances they create, just that the instances respond to a different set of messages the class.

I'm not advocating static methods here. This is something different entirely. Because the class is an object, and can be swapped out for a different object, you're not really statically bound to using that class the same way you would be in Java.

If classes could implement interfaces, you wouldn't have to go through the pain of creating a Factory instance, and passing that in, like this:

ConnectionFactory cf = new ConnectionFactoryImpl()
new ConnectionFactoryClient( cf )

Why go through the pain of creating a new class, and a new instance of a class, when you could use the class object itself. For the most part, classes are factories anyway.

Consider the following common pattern:

class MySQLConnection{
static public void createConnection( String user, String pass ){
new MySQLConnection( user, pass );
}

private MySQLConnection( String user, String pass ){ ... }
}

All the create logic is in one place, and the class is the factory. This, I think, is a good thing.

How could this be done you ask? To make this work with static typing, the language would have to have some construct that allows class objects to implement interfaces. It could look something like so (purpose any syntax you wish):

class MySQLConnection
(class implements ConnectionFactory)
(instances implement Connection){

static public void createConnection( String user, String pass ){
new MySQLConnection( user, pass );
}

private MySQLConnection( String user, String pass ){ ... }
}

We could probably take this even further to allow the constructors to serve as the implementations of the interface methods (maybe by giving constructors aliases).

One final note, in Scala, this would eliminate the need for the top level object that gets created when you define a case class. The class itself could be the object, and it would contain the apply method.

Anyway, that got long. I need to do something to structure this list a bit better.

Wednesday, December 17, 2008

Scala over Ruby

In this post, I'll be maintaining a list of things I like more about Scala, over Ruby. I am also maintaining a similar, opposite list - Ruby over Scala. I plan on maintaining this list here and adding more to it over time, as opposed to several posts. I'm not exactly sure how that works with feeds and things, but oh well.

Also, if at any point I'm totally wrong (which is very possible because I'm new to Ruby), please let me know! It's likely that I just didn't know I could do something in Ruby. I'm eager to learn, and for new ideas, and I'll be more than happy to update the post. Anyway, Onward...


1. Scala doesn't make you use the "." operator when calling methods.

This one I'll try to explain using some simple examples. Here is some Ruby code:

x = 5
y = 6
z = x + y
z2 = x.+y

class ClassWithPlusMethod
def +(other)
# do something, doesnt matter what...
return "whatever"
end
end

x = ClassWithPlusMethod.new
y = ClassWithPlusMethod.new
z = x + y
z2 = x.+y

class SomeOtherClass
def plus(other)
# do something, doesnt matter what...
return "whatever"
end
end

x = SomeOtherClass.new
y = SomeOtherClass.new
z = x plus y

(irb):25: warning: parenthesize argument(s) for future version
NoMethodError: undefined method `plus' for main:Object
from (irb):25

z2 = x.plus y # this is ok!

As you can see, Ruby has magic handling of + mathematical "operator" (and others). "+" is a simple method call, but since it's name is +, Ruby doesn't require the dot, its interpreter handles it differently. This magic is built into the language, and does not extend to methods with regular names, as shown above with "plus".

In Scala, the . operator is not mandatory on any method call. This may seem trivial, but it is not. It helps in creating cleaner DSL's. Take for example, my post on Equalizer.

In Scala, I was able to add the mustBe method to Any, and call it very nicely. But, in Ruby, I had to put in the dot. Contrast these examples:

x mustBe 5

vs

x.must_be 5


2. Method overloading is good.



I use method overloading a lot. An awful lot. I love it. I don't think I need to explain it however.

3. Scala's apply method.



Scala's apply method is something that I'm pretty sure just doesn't exist at all in Ruby, and I'm not sure it can be done easily. For those who don't know what it is, I'll explain, and maybe some Rubyists can show some similar examples. Given that I'm still not a Ruby expert, I could be totally wrong. If so, I would like to know.

For any method called apply, ".apply" can be omitted from the method call. For example given the following definition of the class Array:


class Array{
def get(index:Int) = { ...some code to get from the array... }
def apply(index:Int) = get(index)
}

And an instance of that class:

val a = new Array(whatever)

Then the following calls are essentially equivalent:

a.get(7) // though only because apply calls get
a.apply(7)
a(7)


This is really useful in cleaning up syntax. However, the real beauty of it is hidden below the surface, and will be the subject of a future post.

4. Ruby faking keyword parameters to methods



Calling methods with keyword params is nice for client code readability. For example:

c = httpConnection( :host => "google.com", :port => 80 )

However, in Ruby the niceness ends at the client code. The library code to support this is abysmal. The reason being, for the method using those parameters, its not at all obvious what the method requires. You have to dig down into the implementation to find out what it actually pulls out of params. This is not ok with me. When I look at a method signature, I should be able to understand what dependencies the method has. Example:

def httpConnection(params)
...
...
port = params[:port]
...
...
host = params[:host]
end


5. 1 vs. 3 line method defs.



I run into this one a lot, and find that Ruby code ends up being a lot larger than Scala code for this reason. In Ruby, I can't define a method on one line without it looking simply terrible. Example:

def add7(x)
x + 7
end

or

def add7(x); x + 7; end

The first version is 3 lines when it doesn't need to be. The second version is one line littered with noise.

Here's the much simpler Scala version:

def add7(x:Int) = x + 7

While this entire point might sound trivial, its not. Functional style encourages us to write many small methods. Ruby code grows larger than Scala code quickly. The problem also becomes bad when using nested functions. Ruby:

def add7(x)
def add3
x + 3
end
add3 + 4
end

Scala:

def add7(x:Int) = {
def add3 = x + 3
add3 + 4
}


All of this might seem rather trivial, but in practice it definitely adds up.

Tuesday, December 16, 2008

Coming Soon

For people that care (probably just myself, but I hold out hope), I'm going to spew out a list of the things I'm working on, posts that can be expected in the near future, and other random crap.

  1. The project I was working on was indeed cancelled, as predicted. In hindsight, I'm coming out looking pretty smart. I expect to write some more of my true feelings on this situation. One sad thing of course is that my good friends and old coworkers may soon have to look for new jobs. I hope not.
  2. Ruby is nice. I won't say that it's not as nice as Scala, as I may be attacked by the very vocal Ruby community. But I will say that I enjoy writing Scala much more (I do plan to expand on why, but this isn't the right time). However, some of the dynamic things you can do with Ruby are fascinating.
  3. Rails is nice as well, though I think it has its flaws. I hope to learn Lift very soon and do a nice comparison. We'll see if I have enough time.
  4. Today I started reading about building Facebook apps in Rails. This is something I'll likely dedicate a lot of time to.
  5. Yesterday I learned a bunch about iPhone development. I haven't written anything yet, just had a big walk-through of a pretty popular application. At first glance it seemed fantastic as Apple has made creating views quite simple. This is great because I'm terrible at any visual stuff. Anyway, this is the thing that I will probably end up dedicating the most time to; mostly because I still hold out hope for entrepreneurship.
  6. I am loving my new job. Leaving NYSE has turned out to be a fantastic decision. My new team is great. I'm re-energized. I'm challenged. I'm actually learning at work, instead of just at home. Learning is encouraged, not shunned. I love it.
  7. Lastly, I told myself about a year ago that I wouldn't be getting back into web development. This has changed for a few reasons:

    1. I will still never ever ever try to make things look nice.
    2. It seems like the frameworks available today eliminate most of the rest of the crap that I didn't want to do before.
    3. Having immediate access to millions of users on Facebook seems really exciting, eliminating more crap that I was never any good at - getting people to come to my site.
    4. Most importantly, I have an opportunity to learn new languages, and obviously that's what I really care about

Friday, November 28, 2008

foldLeft in Scala, Little Schemer style

I'm going to write up a Scala version of foldLeft in the style of The Little Schemer.

What is 0 + (1 + 2 + 3)?

>6

What is 0 + (1 + 2 + 3)?

>0 + 1 + (2 + 3)

What is 0 + 1?

>1

What is 1 + (2 + 3) ?

>1 + 2 + (3)

What is 1 + 2?

>3

What is 3 + (3)?

>3 + 3

What is 3 + 3?

>6

Are we done?

>No, we still haven't found out what foldLeft is.

What is foldLeft?

def foldLeft[A, B](as: List[A], z: B)(f: (B, A) => B): B = {
as match {
case Nil => z
case x :: xs => foldLeft( xs, f(z, x) )( f )
}
}

But that doesn't tell us much does it? Let's walk through an example.

What is List( 1, 2, 3 )?

>List( 1, 2, 3 )

What is foldLeft(a, 0){ (x,y) => x + y } when a is List( 1, 2, 3 )

>6 ... but why? Let's step through it together.

What is the first question foldLeft asks about the list?

>case Nil

Is a Nil?

>No, it's List( 1, 2, 3 ), so we ask the next question.

What is the next question?

>case x :: xs

What is the value of case x :: xs?

>true, because the list is not Nil, it contains one element x which is 1, followed by a list xs which is List(2,3).

So what is the next step?

> foldLeft( xs, f(z, x) )( f )

What is f( z, x )?

> Well, remember, we called foldLeft like so: foldLeft(a, 0){ (x,y) => x + y }

And what is f?

> { (x,y) => x + y }

Again, what is f( z, x )?

> f( 0, 1 )
> (0,1) => 0 + 1
> 1

So what has foldLeft( xs, f(z, x) )( f ) become?

> foldLeft( List(2,3), 1 )( f )

Now we recur into foldLeft. What is the first question foldLeft asks about the list?

>case Nil

Is a Nil?

>No, it's List( 2, 3 ), so we ask the next question.

What is the next question?

>case x :: xs

What is the value of case x :: xs?

>true, because the list is not Nil, it contains one element x which is 2, followed by a list xs which is List(3).

So what is the next step?

> foldLeft( xs, f(z, x) )( f )

What is f( z, x )? Remember that z is now 1.

> f( 1, 2 )
> (1,2) => 1 + 3
> 3

So what has foldLeft( xs, f(z, x) )( f ) become?

> foldLeft( List(3), 3 )( f )

Now we recur into foldLeft. What is the first question foldLeft asks about the list?

>case Nil

Is a Nil?

>No, it's List(3), so we ask the next question.

What is the next question?

>case x :: xs

What is the value of case x :: xs?

>true, because the list is not Nil, it contains one element x which is 3, followed by a list xs which is Nil.

So what is the next step?

> foldLeft( xs, f(z, x) )( f )

What is f( z, x )? Remember that z is now 3.

> f( 3, 3 )
> (3,3) => 3 + 3
> 6

So what has foldLeft( xs, f(z, x) )( f ) become?

> foldLeft( Nil, 6 )( f )

Now we recur into foldLeft. What is the first question foldLeft asks about the list?

>case Nil

Is a Nil?

>Yes

So what do we do?

> case Nil => z

And what is z?

6!

So what is foldLeft(a, 0){ (x,y) => x + y } when a is List( 1, 2, 3 )

6!

Are we done?

Yes! Now foldLeft a taco right into your mouth.

Monday, November 24, 2008

Refactoring Imperative Code To Functional Code

I've been refactoring Scala literally for days. It's fantastic how much I've learned over the last year. I knew a little bit about functional programming from doing Lisp in college, but a year and a half ago I couldn't have given you the definition of it.

I decided to tackle some of the most obvious (and ugly) imperative/procedural code in my CPU simulator and turn it into an elegant, functional style.

I'll paste the original code here, then explain it a bit, then show the refactorings one step at a time. In explaining, I will assume that you know at least a bit about how anonymous functions work in Scala.


class EightBitAdder( a: EightBitNumber,
b: EightBitNumber,
carryIn: PowerSource ) {

private val fullAdders: Array[FullAdder] = createFullAdders( a, b, carryIn )
private val output: EightBitNumber = createOutput()

def getOutput: EightBitNumber = output
def getCarryOut: PowerSource = fullAdders(7).getCarryOut


private def createFullAdders( a: EightBitNumber,
b: EightBitNumber,
carryIn: PowerSource ): Array[FullAdder] = {
val fullAdders = new Array[FullAdder](8)
fullAdders(0) = new FullAdder( a(0), b(0), carryIn );
for( i <- 1 until 8 ){
fullAdders(i) = new FullAdder(a(i),b(i), fullAdders(i-1).getCarryOut);
}
fullAdders
}

private def createOutput(): EightBitNumber = {
val out = new Array[PowerSource](8)

var count = 0;
fullAdders.foreach( p => {
out(count) = p.getSumOut
count = count + 1
}
)
new EightBitNumber(out)
}
}


This code was designed to build an 8 bit adder out of two 8 bit numbers (numbers in this particular case aren't much more than arrays of bits) and a carry in bit. This is your typical, ordinary, everyday 8 bit adder that you much have seen in 1950. The adders job is simple, output the result of the two input numbers added up. As with any 8 bit adder, there are 9 outputs, 8 standard output bits, and the carry out/overflow bit.

The adder accomplishes addition in a standard fashion, by chaining 8 full adders (one bit adders) together. The first full adder in the chain uses the given carry in bit as its carry in bit, and subsequent adders in the chain use the carry out of the previous full adder as the carry in. The carry out of the entire adder is simply the carry out of the last full adder in the chain. Here is a picture of one:



Now that we have all the background out of the way, I'll start the refactorings. I'm actually going to go a little bit in reverse order, refactoring the createOutput() method first, because it is substantially easier to refactor than the createFullAdders method.

Simple Refactoring


Lets take another look at createOutput:

private def createOutput(): EightBitNumber = {
val out = new Array[PowerSource](8)

var count = 0;
fullAdders.foreach( p => {
out(count) = p.getSumOut
count = count + 1
}
)
new EightBitNumber(out)
}

This method is returning an EightBitNumber, which is really just an array holding the 8 output bits. The code is terribly imperative, and terribly terrible. The sad thing is, I actually wrote this code, and I'm not just making up a bad example :( Anyway, its overall strategy is pretty clear.

  1. Create an empty, length 8 array
  2. Create a counter object for indexing into the array
  3. Loop over all the full adders (those are already create by the time this method gets called, and well see that in a bit)
  4. For each adder: Put each full adders sum out into the array, and increment the counter.
  5. Finally, create an 8 bit number object using the array.

The first 4 steps above are there simply to create the array to pass to the EightBitNumber object. Now lets take a look at the refactored code:

private val output = new EightBitNumber(fullAdders.map(fa => fa.getSumOut))

Wow! That looks a lot easier - 12 lines down to 1! But...some people might not know what it does, so I'll do my best to explain. The map method, which is a method on all Seq objects (short for Sequence; Array is a subclass), "Returns the list resulting from applying the given function f to each element of this list." An example should help.

Given a=List(1,2,3,4,5) then a.map( i => i * 10 ) returns List(10,20,30,40,50). i * 10 was applied to each element "i" in the list.

In the cpu simulator code above, the call to map has built an Array containing the sumOut of each full adder using the function fa => fa.getSumOut.

Slightly More Difficult Refactoring


With the easier part out of the way, I tackled the more difficult createFullAdders. Let's review the original implementation again.

private def createFullAdders( a: EightBitNumber,
b: EightBitNumber,
carryIn: PowerSource ): Array[FullAdder] = {
val fullAdders = new Array[FullAdder](8)
fullAdders(0) = new FullAdder( a(0), b(0), carryIn );
for( i <- 1 until 8 ){
fullAdders(i) = new FullAdder(a(i),b(i), fullAdders(i-1).getCarryOut);
}
fullAdders
}

This method is responsible for creating all the full adders, and chaining them together. The createOutputs method was only responsible for getting all the outputs off of the full adders created here.

Similar to the last method, this method uses an imperative style, creating an array, populating it, and finally returning it. It's quite a bit trickier though because of the chaining. You can't simply use the map function because there's no context in map. Here, each new full adder needs to know about the preceding full adder. This guy is going to be a bear to explain, but let me just go ahead and dump the code on you:

val (fullAdders, carryOut) =
(as zip bs).foldLeft((List[FullAdder](),carryIn)){
case ((current, carry), (a, b)) =>
val adder = new FullAdder(a, b, carry)
(current ::: List(adder),adder.carryOut)
}


With James Iry's help, we've made this code about as simple as possible. With the first pass, I wasn't sure if the functional code was more readable than the imperative, but after he helped me clean it up, I'm positive. Now, if you aren't familiar with some of the concepts contained in that code, you might be thinking, "What are you $%^&ing nuts?" But, I'm convinced that after you get used to reading this, it's so much easier to read, and so much less error prone, and so much more natural, that you'll never go back. Honestly, after leaving this project alone for almost a year and coming back to it and finding the imperative code, I almost threw up in my mouth a little.

Okay, now I'll try to explain these concepts, and most likely fail miserably.


  1. First, and simplest, is zip. This one is pretty easy. Taken right from the Scaladoc - zip:

    "Returns a list formed from this list and the specified list 'that' by associating each element of the former with the element at the same position in the latter. If one of the two lists is longer than the other, its remaining elements are ignored."


    I think a few examples will explain perfectly.

    Given a=List(1,2,3) and b=List(a,b,c) then a.zip(b) will return List((1,a), (2,b), (3,c)).
    Given a=List(1,2,3) and b=List(a,b,c,x,y,x) then a.zip(b) will return List((1,a), (2,b), (3,c)), as the remaining elements in b are ignored.

    The code in the cpu simulator zips as and bs, which associates the appropriate input bits together. Take a quick look back at the picture to see that this returns ((a0,b0),(a1,b1),(a2,b2),(a3,b3),(a4,b4),(a5,b5),(a6,b6),(a7,b7)).

  2. Next is foldLeft, which is a bit more complicated. Once again, from the Scaladoc - foldLeft:

    Combines the elements of this list together using the binary function f, from left to right, and starting with the value z.



    This one I've written up separately, because it was so long. You can find it at http://jackcoughonsoftware.blogspot.com/2008/11/foldleft-in-scala-little-schemer-style.html


  3. Next is pattern matching, but I have to go to bed again! At least I've made some progress :)



Revised Code


Here is the finshed product, which no longer uses 8, but instead creates adder chains of N, depending on the length of the inputs. Overall, I think it's a vast improvement over the original.


class AdderChain(as: Number, bs: Number, carryIn: PowerSource) {

if( as.size != bs.size ) error("numbers must be the same size")

val (fullAdders, carryOut) =
(as zip bs).foldLeft((List[FullAdder](),carryIn)){
case ((current, carry), (a, b)) =>
val adder = new FullAdder(a, b, carry)
(current ::: List(adder),adder.carryOut)
}

val output = new Number(fullAdders.map(fa => fa.sumOut))
}

Using Scala Implicits to Replace Mindless Delegation

I'm still refactoring my Scala CPU Simulator code, as I keep finding ways to just lop off piles of unneeded code. In this latest example, I was using pretty standard Java style delegation - having my class implement an interface, having a member variable of that interface, and delegating all method calls on that interface to the member variable.

There are several problems with this:

  1. The main problem: if I add a method to the interface I then have to add it to everyone implementing the interface. But, what If I'm not actually writing the implementation of the interface? Client code won't compile. Adding an implicit doesn't remove this problem entirely, but it certainly works for plain old delegates.

  2. It's error prone. Maybe the method was a void, and my IDE added the signature for the method, so the code compiles, but I forgot to actually delegate to the member.
  3. It's just plain wordy and ugly.


To remove the boilerplate, all I needed to do was add an implicit conversion from my class to the interface, using the member variable. I'll show this below.

First, here is an example of the old, more wordy style:

trait PowerSource{
def connect( p: PowerSource ): Unit
def disconnect( p: PowerSource ): Unit
def reconnect( p: PowerSource ): Unit
}

class DelegateToPowerSource( in: PowerSource ) extends PowerSource {
def connect( p: PowerSource ) = in connect p
def disconnect( p: PowerSource ) = in disconnect p
def reconnect( p: PowerSource ) = in reconnect p
}


DelegateToPowerSource has a member, "p", and implements the PowerSource interface by delegating to that member for each of the methods on the PowerSource interface. The more methods that PowerSource has, the longer DelegateToPowerSource gets, and yet the code is just boilerplate. Even if the IDE does this for you, its still wordy and potentially error prone.

Now for the new version:


trait PowerSource{
def connect( p: PowerSource ): Unit
def disconnect( p: PowerSource ): Unit
def reconnect( p: PowerSource ): Unit
}

object DelegateToPowerSource{
implicit def delegateToPowerSource( d: DelegateToPowerSource ) = d.p
}

class DelegateToPowerSource( p: PowerSource )


That's it. Now, any time I add a method to the PowerSource interface (I should probably start calling it trait), DelegateToPowerSource simply has that method; via the conversion. I never have to change DelegateToPowerSource because of a change to PowerSource. DelegateToPowerSource can simply have whatever code in it that it was originally intended to have, obviously augmenting PowerSource in some way.


For completeness, I'll post the actual code where I did exactly this. But, it's pretty much the same, so if you get the point, no need to keep reading.


trait LogicGate extends PowerSource{
val inputA: PowerSource
val inputB: PowerSource
val output: PowerSource
}

abstract class BaseLogicGate(val inputA: PowerSource, inputB: PowerSource) extends LogicGate {

def state = output.state

def -->( p: PowerSource ): PowerSource = output --> p
def <--( p: PowerSource ): PowerSource = output <-- p

def disconnectFrom( p: PowerSource ): PowerSource = output disconnectFrom p
def disconnectedFrom( p: PowerSource ): PowerSource = output disconnectedFrom p

def handleStateChanged( p: PowerSource ) = {}
def notifyConnections = {}
}

class AndGate(a: PowerSource, b: PowerSource)
extends BaseLogicGate(a: PowerSource, b: PowerSource){
val output = new Relay(a, new Relay(b))
}


Of course there were several other LogicGates (or, nor, nand, etc). All of this was condensed down to:


object LogicGate{
implicit def logicGateToPowerSource( lg: LogicGate ): PowerSource = lg.output
}

trait LogicGate{
val inputA: PowerSource
val inputB: PowerSource
val output: PowerSource
}

class AndGate(val inputA: PowerSource, val inputB: PowerSource) extends LogicGate{
val output = new Relay(inputA, new Relay(inputB))
}


BaseLogicGate is now removed entirely. This is great because BaseLogicGate was really weird, it didn't even use its inputs. The only reason it was there was to decouple the delegation logic from the actual trait.

Now things have become MUCH more clear. AndGate is a LogicGate with inputs A and B, and one output, made from Relays.

Tuesday, November 18, 2008

Equalizer

I wrote a cool Equalizer class in Scala that allows me to do assertions that are more readable than traditional assertions.

Quick side note: (Equalizer is really an idea shamelessly stolen from Bill Venners Equalizer in ScalaTest. Hopefully we'll add my methods in as well.)

My Equalizer lets me do things like:

val x = 5
x mustBe 5

This replaces the more common assertEquals( x, 5 ), and I think it does so nicely.

You can also do a few more sophisticated things with it, like so:

val x = 5
x mustBe ( 3 or 4 or 5 )

I probably could have used "in" here, such as x mustBe in( 3, 4, 5 ) ... what do you think?

Additionally:

val x = 5
x cantBe 6

For whatever this one is worth (I've actually found use cases for it):

val x = false
x canBeNullOr false

val y = 6
y canBeNullOr ( 5 or 6 )


This works by implicitly converting Any to Equalizer, which contains the methods above. The code can be found below.

import org.testng.Assert._

case object Equalizer {
implicit def anyToCompare(a: Any) = new Equalizer(a)
}

class Equalizer(a: Any) {

def mustBe(bs: Any*): Unit = {
bs(0) match {
case x:MyTuple => x mustBe a
case _ => {
val message = "In Equalizer: expecting one of=" + bs + "\nIn Equalizer: actual =" + a
println(message)
bs size match {
case 1 => assertEquals(a, bs(0), message)
case _ => assertTrue(bs.contains(a), message)
}
}
}
}

def canBeNullOr(bs: Any*) = {
if (a != null) mustBe(bs: _*)
else println("In Equalizer: expecting one of=" + bs + " or null\nIn Equalizer: actual =" + a)
}

def cantBe(b: Any) = assertFalse(a == b)

def is(b: Any) = a equals b

def or(b: Any) = {
a match {
case x:MyTuple => x + b
case _ => MyTuple2(a, b)
}
}

import Equalizer._

trait MyTuple{
def +(b: Any): MyTuple
def mustBe(a: Any): Unit
}
case class MyTuple2(y: Any, z: Any) extends MyTuple{
def +(b: Any): MyTuple = MyTuple3(y, z, b)
def mustBe(a: Any): Unit = a mustBe (y,z)
}
case class MyTuple3(x: Any, y: Any, z: Any) extends MyTuple{
def +(b: Any): MyTuple = MyTuple4(x, y, z, b)
def mustBe(a: Any): Unit = a mustBe (x,y,z)
}
case class MyTuple4(w: Any, x: Any, y: Any, z: Any) extends MyTuple{
def +(b: Any): MyTuple = MyTuple5(w, x, y, z, b)
def mustBe(a: Any): Unit = a mustBe (w,x,y,z)
}
case class MyTuple5(v: Any, w: Any, x: Any, y: Any, z: Any) extends MyTuple{
def +(b: Any): MyTuple = MyTuple6(v, w, x, y, z, b)
def mustBe(a: Any): Unit = a mustBe (v,w,x,y,z)
}
case class MyTuple6(u: Any, v: Any, w: Any, x: Any, y: Any, z: Any) extends MyTuple{
def +(b: Any): MyTuple = throw new IllegalArgumentException("too many ors")
def mustBe(a: Any): Unit = a mustBe (u,v,w,x,y,z)
}
}


Sorry about MyTuple...I wanted people to be able to use Tuples as arguments in their mustBe statements, so I had to make sure I didn't pass in a Tuple into mustBe, via the "or" method. Anyway, Tuples don't even appear to be working so....ugh... If anyone can help me clean this up, that would be awesome.

Regardless, what do you think? I really like using the code in tests, even if the Equalizer class itself is a bit hairy.

Monday, November 17, 2008

Refactoring Scala: My CPU Simulator Revisited

I'm preparing to learn Ruby (though I've already tinkered with it some), and to do so, I'm going to revisit my CPU Simulator project that helped me learn Scala so well. I'm going to write it again in Ruby.

So today, I took up revisiting it, with the goal in mind of writing some Ruby. Turned out that didn't actually happen. What did happen was a lot of refactoring of the original Scala code. I hadn't touched that code in several months, and in between then and now I've written a LOT of Scala. Here's some of the things I've learned (and refactored).

  1. I used to use way too much redundant type information. This was a natural habit from writing Java for so long (in fact, pretty much all my bad habits stem from too much Java). I rigorously removed ALL the obviously redundant type declarations. I did find that in some cases it helped to have it there, that the code wasn't exactly clear without it, and so I left it. I'm very interested to see what happens here when I slide over to Ruby.
  2. Out of habit, I used a lot of unneeded semi-colons. I removed all of them. I hate semi-colons. It's official.
  3. I got a lot better at functional programming. There were a lot of areas where I should have used functions, and I refactored the code to do so. My line of code cound is down considerably.
  4. Finally, I removed all the Hamcrest matchers. This one I'll explain in more detail in my post tomorrow. I'm basically using my own assert library that allows me to say things like: x mustBe 5 I prefer this style to any other assertions I've come across.

Sunday, November 16, 2008

Back

For the past several months I've been giving my life to a cause that I now believe will fail miserably. I've decided to leave the NYSE. I wasn't being challenged technically, and management was simply not up to snuff. They actually asked me to, "just drink the kool-aid". I swear.

I haven't been writing, and I haven't even been coding much, all to work on this Death March project. Basically, its been terrible, and I feel like I went into a coma and I've just come out. I'm going to start writing again passionately.

I've accepted a new position where I'll be writing IPhone applications, Facebook apps with Rails, other web work with Rails, etc. I'm very excited about it. I get to learn two languages that I have little experience with (Ruby and Objective C). I get to work with a team that is much more in line with my way of thinking - adopting new technology, open-minded, agile, lots of tests, curious. It feels like a giant weight has been lifted off of my back. I'm very excited.

Additionally, I won't have to work in Java anymore. I'm convinced at this point that java is a dying language. I heard Neal Gafter left Google to work on languages at Microsoft.

I feel his situation parallels mine. He worked tirelessly on closures for Java 7, which he truly believed (as do many) were right for the language. But, the JCP is so damned conservative, that not only will his closures probably not make it into Java 7, but come on...will Java 7 ever actually come out?

I worked tirelessly for NYSE, trying to introduce new technology and exciting ideas. I tried to bring in Scala, and was shot down. I tried to bring in a test first attitude and stress that we really needed time to work on the testing framework there in general, only to be shot down at every suggestion. I felt the same as I imagine Neal felt, "This is impossible".

I believe NYSE ATS software projects will continue to fail until management is replaced.

This was a bit of a rant, but it was a long time coming.

Saturday, September 13, 2008

Language Feature Request

Maybe this feature exists in some language, I'm not sure. My inexperience is letting me down. :( Here is what I want, as demonstrated in Scala.

I want to be able to use the name of my variable programmatically. So, instead of having to give my objects names like this:


case class Server( name: String )
val server = Server("Altair")
println(server)


Which yields: Server("Altair")


or like this:


class Server( name: String ){ override def toString = name }
val server = new Server("Altair")
println(server)


Which yields simply: Altair


I would like something like this:


case class Server extends VariableName
val Altair = new Server
println(Altair)


Which yields simply: Altair

That example shows it as simply a library. It probably can't be done as a library, so it seems like it would have to be a language feature. Something like this.


varname case class Server
val Altair = new Server
println(Altair)


Which yields simply: Altair


Does anything like this exist? Would it be terribly difficult to build into a compiler? Things would probably be tricky if you said something like...


varname case class Server
val Altair = new Server
val Moxy = Altair
println(Moxy)


Would you want to get Altair, or Moxy?

Can anyone give any opinions on this at all?

Sunday, July 06, 2008

Using Scala Actors

I'm assuming (maybe incorrectly) that most of the Actors that will be written will simply want to react to messages, forever. Something like this:

val reactor = new Actor(){
def act() {
loop{
react{
case msg => ...
}
}
}
}

Given that assumption, it seems like it would be nice just to define whats in the react portion of the code. The rest is redundant. This is pretty simple. First, I created a simple little factory called Actors.

object Actors{
def newReactor( f: PartialFunction[Any,Unit] ): Actor = {
new Actor(){ def act() { loop{ react(f) } } }
}
}

and then I simply used it:

val reactor = Actors.newReactor {
case msg => println( "Got something: " + msg )
}

This consolidated the code outside the actual reaction from 4 lines (and 4 right brackets) to a single line (and a single right bracket).

You can also do some other interesting which allow you to keep your reaction code separate from the actual actors (you can do this using the original approach as well). You can define partial functions, and pass them into the newReactor method like this:

def normalReaction : PartialFunction[Any,Unit] = {
case x: int => println( "Got int: " + x )
case msg => println( "Got something else: " + msg )
}

def abnormalReaction : PartialFunction[Any,Unit] = {
case msg => println("eruhewiurhqweihu!!!!")
}

val normalReactor = Actors.newReactor { normalReaction }
val abnormalReactor = Actors.newReactor { abnormalReaction }


I know this is all rather simple and trivial, but I'm crazy about reducing redundancy and improving readability.