Symmetric Sympathy

I am a software developer. I’ve programmed in around twenty different programming languages since I was eleven years old. I spent the last seven years of the previous century coding in an amazing language called Smalltalk. I have spent the first seventeen years of this century coding primarily in the Java language, which thankfully continues to improve.

Smalltalk is about big dreams. Java is about little realities.

Big dreams inspire great things. Software development today is becoming incredibly complex. There is still a lot we can learn from how to scale to handle that complexity from Smalltalk.

I am a committer for an open source Java Collections framework called Eclipse Collections which was inspired by my experiences using Smalltalk back in the 90's. Eclipse Collections has been evolving for 12+ years. Symmetry drives a lot of the work in Eclipse Collections. I like to say that symmetry is like gravity. When I see missing or dissimilar patterns, I feel the weight of symmetry. It is work that has yet to be done.

What is Symmetry?

Symmetry is the similarity between different things. In a system with good symmetry, you will see the similarities, and where there is not good symmetry, you will discover the differences.

Scope of Symmetry in Eclipse Collections

The picture above represents the combination of features available in Eclipse Collections. We have an API for filtering, which is called select. When there is good symmetry for select, it will be available across all data structures for eager/lazy behavior, serial/parallel execution, readable/mutable/immutable interfaces, object and primitive versions of each container.

A snapshot of the co-variant forms of the “select” API in the RichIterable hierarchy

In the picture above, you will see the select API defined across several interfaces in the Eclipse Collections type hierarchy. On RichIterable, select returns RichIterable. Each subtype of RichIterable defines a covariant override for select. On ListIterable, select returns ListIterable. On LazyIterable, select returns LazyIterable. MutableList returns MutableList and ImmutableList returns ImmutableList, etc.

There are other forms of symmetry as well. For every data structure, there is usually a corresponding Readable (e.g. ListIterable), Mutable (e.g. MutableList) and Immutable (e.g. ImmutableList) interface. For most types, this will extend across both object and primitive containers (e.g. IntList, MutableIntList, ImmutableIntList, DoubleSet, MutableDoubleSet, ImmutableDoubleSet, etc.).

A large system with good symmetry becomes easier to understand, because you can detect and expect recurring patterns.

Turtles all the way down

“One of these things is not like the others…” — Sesame Street

In Smalltalk, everything is an object. It’s “turtles all the way down”. This makes good symmetry easier to achieve. In Java, everything is not an object. Java has eight primitives (boolean, byte, char, double, int, float, long, short). Primitives and objects behave differently. Primitives are the little realities of Java. Achieving good symmetry across objects and primitives in a collections framework is a challenge.

We face this challenge with grit. Eclipse Collections has support for both object and primitive collections. This can have tremendous benefits (efficiency/performance/fluency) and unfortunate costs (effort/time/code size). We fix missing symmetry when we find it, but only when we know there is a use case for it. Code generation helps reduce the amount of human work significantly, but can create a lot of duplicate code if we’re not careful.

If you are programming in Java today, check out Eclipse Collections. This amazing collections framework makes Java better and more fun to program in. If you start to use it in your projects, you will understand why I have developed a lot of sympathy for symmetry. Symmetry makes learning and using a framework as feature rich and large as Eclipse Collections much easier for developers. In future blogs, I plan to highlight where symmetry is helping to evolve the development of the framework.

“The best way to predict the future is to invent it.” — Alan Kay

I still code in Smalltalk when I can find the time. Smalltalk reminds me of how things once were and how they can be again when we learn from the past and share those lessons with others. I am happy knowing that there are developers out there still working hard on keeping the Smalltalk language and community vibrant and growing. If you don’t know or haven’t used Smalltalk in a while and want to see what you are missing, have a look at Pharo Smalltalk or Dolphin Smalltalk. They are both great open source Smalltalk development environments.