Newsletter sign-up
View all newsletters

Enterprise Java Newsletter
Stay up to date on the latest tutorials and Java community news posted on JavaWorld

Sponsored Links

Optimize with a SATA RAID Storage Solution
Range of capacities as low as $1250 per TB. Ideal if you currently rely on servers/disks/JBODs

Clojure: Challenge your Java assumptions

Let this functional language for the JVM redefine your approach to software design

  • Print
  • Feedback

Clojure is a dynamic functional language for the JVM, recently released in version 1.0. Clojure offers a new set of programming techniques for robust code and rapid development. In particular, it has new solutions for multicore computing. Whether you make the shift to Clojure or stick to Java, learning about this new language will challenge your assumptions about the best way to design software.

Clojure is a new language for the JVM. Like Groovy, Jython, and JRuby, it offers dynamism, conciseness, and seamless interoperability with Java.

Clojure is a dialect of Lisp, recently released in version 1.0. Developers often dismiss Lisp as impractical, perhaps because of its distinctive syntax, its ascetic simplicity, or the academic uses it's often applied to. Clojure is set to break that curse. Rich Hickey designed the language to make it easy and practical to take on the same sorts of problems you handle with Java, more robustly and with less code.

Any new programming language, no matter how good, has to find its killer app to break through into widespread use. Clojure's killer app is parallel programming for multicore CPUs, which are now the major route to increased processing power. With its immutable datatypes, lockless concurrency, and simple abstractions, Clojure makes multithreading simpler and more robust than in Java.

I'll describe some of Clojure's distinctive features and show how applying lessons from the language can make your Java code more elegant and less buggy. I hope that you come away wanting to learn more.

Code as data

Let's start with the simple function in Listing 1, which calculates the area of a circle.

Listing 1. A simple Clojure function

(defn
   circle-area [r] 
    (* Math/PI r r))

Clojure code looks quite different from Java code, for a simple reason. In Clojure, code is data; it is built from exactly the same lists and vectors as any other data structure. The consistent homoiconic syntax makes it easier for both programmers and programs to understand and manipulate the code.

So, the function definition in Listing 1 is nothing but a list (marked with parentheses), holding a vector (marked with square brackets) and another list. The list syntax in the first line defines the function. After the function name, a vector holds the parameters. And in the last line, the list syntax invokes the function of multiplication, applied to three operands.

Clojure's minimalist syntax becomes quite readable with even a little practice. Support for Clojure in all major development environments -- including NetBeans, IntelliJ, and Eclipse, as well as vi and Emacs -- makes it even easier to handle. Figure 1 shows an example from VimClojure, where paired parentheses are matched by color. (The function extracts lower-case characters from a string: (get-lower "AbCd") is "bd".)

Figure 1. Clojure support in Vim

Figure 1. Clojure support in Vim (Click to enlarge.)

In fact, because of its lightweight syntax, a Clojure program is often simpler than the equivalent Java. The Java getLower() function in Listing 2, for example, has twice the brackets and four times the code as the Clojure function.

  • Print
  • Feedback

Resources
  • Visit the main Clojure site for downloads, documentation, and references to articles, tutorials, examples, podcasts, and videos.
  • The first book published on Clojure, Programming Clojure (Stuart Halloway, Pragmatic Programmers, 2009) is an excellent introduction and guide to the language.
  • The four articles in "Java.next" (Stuart Halloway, JavaWorld, 2008) discuss new languages for the JVM, including Clojure. Each one goes into a different aspect of Clojure, including immutability and Java interoperation.
  • In "Clojure or Scala: Which is poised for stardom?" Andrew Glover summarizes the differences between these two functional languages for the JVM.
  • Meikel Brandmeyer's VimClojure (which has merged with the former Gorilla project) consists of a set of plug-ins for Vim to facilitate editing of Clojure files.
  • "Understanding Clojure's PersistentVector implementation" (Karl Krukow, Higher Order, 2009) explains Clojure's vector implementation.
  • Webjure is a Web framework for Clojure. Although Java-language libraries are accessible in Clojure, native libraries fit better with Clojure's coding style. Such libraries are now appearing at a rapid pace.
  • "Lazy programming and lazy evaluation" (Jonathan Bartlett, IBM developerWorks, 2006) shows how to apply some functional-programming ideas to Java -- harder than Clojure, but possible.
  • "Lisp: Good News Bad News How to Win Big" (Richard Gabriel, 1991) is the classic explanation of why Lisp never caught on in widespread commercial use.
  • "Ruby for the Java World" (Joshua Fox, JavaWorld, 2006) compares Java with Ruby, another dynamic language for the JVM. Ruby has been called "an acceptable Lisp."
  • According to "The concurrency support in Java 7 is not enough" (Henrik Engström, Recursion: See Recursion, 2008), Java is still inadequate for the multicore challenge.
  • "Multicore processing for client-side Java applications" (Kirill Grouchnikov, JavaWorld, 2007) takes on the multicore challenge in client-side Java programming.
  • Java Concurrency in Practice (Brian Goetz et al., Addison-Wesley, 2006) is the best guide to multithreaded programming in Java.
  • Read about another functional-programming concept brought to Java in "Memoization in Java Using Dynamic Proxy Classes" (Tom White, On Java, 2003).

More from JavaWorld