Core Java

Functional Java by Example | Part 1 – From Imperative to Declarative

Functional Programming (FP) is about avoiding reassigning variables, avoiding mutable data structures, avoiding state and favoring functions all-the-way. What can we learn from FP if we would apply functional techniques to our everyday Java code?

In this series called “Functional Java by Example” I will refactor in 8 installments an existing piece of code to see if I can reach Functional Nirvana in Java.

I don’t have much experience in a “real” functional language such as Haskell or F#, but I hope to demonstrate in each article by example what it means to apply some of these practices to your every day Java code.

Hopefully at the end you’ve gained some insight and know to pick some techniques which would benefit your own codebase.

These are all the parts:

  • Part 1 – From Imperative to Declarative
  • Part 2 – Naming Things
  • Part 3 – Don’t Use Exceptions to Control Flow
  • Part 4 – Prefer Immutability
  • Part 5 – Move I/O to the Outside
  • Part 6 – Functions as Parameters
  • Part 7 – Treat Failures as Data Too
  • Part 8 – More Pure Functions

I will update the links as each article is published. If you are reading this article through content syndication please check the original articles on my blog.

Each time also the code is pushed to this GitHub project.

Disclaimer: code is written in Apache Groovy, primarily for conciseness, so I don’t have to type stuff (you know: typing) where it doesn’t matter for the examples. Secondary, this language Just Makes Me Happy.

Why should you care about Functional Programming (FP)?

If you’re not doing Haskell, F# or Scala on a hip real-time, streaming data event processing framework you might as well pack your bags. Even the JavaScript guys are spinning functions around your methods these days — and that language has been around for some time already.

There are a lot of articles and video’s out there which make you believe that if you don’t hop on the Functional bandwagon these days, you’re left behind with your old OOP-contraptions and frankly, are obsolete within a couple of years.

Well, I’m here to tell you that’s not entirely true, but FP does have some premises, such as readability, testability and maintainability, values which we also strive to achieve in our (enterprise) Java code right?

As you’re reading this, for years you might already have the same outspoken opinion about FP being a step forwards or backwards or anno 2017-2018 you are just open for new ideas

You can level up your skills in every language by learning FP.

Determine for yourself what you can learn from it and how your own programming can benefit from it.

If you’re up to the task, let’s start this series with…

Some existing code

A word about example code: It’s pretty tricky to come up with contrived examples for blogs like these: it should be easy enough to appeal to a broad audience, simple enough to be understood without too much context, but still be interesting enough to result in desired learning effects.

Moving forward, each installment in this series will build on the previous one. Below is the code we’re going to take as a starting point.

So, put on your glasses and see if you’re familiar with coding-style below.

class FeedHandler {

  Webservice webservice
  DocumentDb documentDb

  void handle(List<Doc> changes) {

    for (int i = 0; i < changes.size(); i++) {
      def doc = changes[i]
      if (doc.type == 'important') {

        try {
          def resource = webservice.create(doc)
          doc.apiId = resource.id
          doc.status = 'processed'
        } catch (e) {
          doc.status = 'failed'
          doc.error = e.message
        }
        documentDb.update(doc)
      }
    }
  }
}
  • It’s some sort of FeedHandler.
  • It has two properties, some Webservice class and a DocumentDb class.
  • There’s a handle method which does something with a list of Doc objects. Documents?

Try to figure out what’s going on here

..

..

..

Done?

Reading stuff like this can make you feel like a human parser sometimes.

Scanning the class name (FeedHandler?) and the one method (void handle) can give you, next to some eye sore, a “feel” for the purpose of everything.

However, figuring out what exactly gets “handled” inside the handle method is much harder.

  • There’s a for-loop there — but what’s exactly being iterated? How many times?
  • This variable webservice is called, returning something called resource.
  • If webservice returns successfully, the doc (a document?) being iterated over is updated with a status.
  • Seems webservice can also throw an Exception, which is caught and the document is updated with another status.
  • Ultimately, the document is “updated” by this documentDb instance. Looks like a database.
  • Oh wait, this happens only for the “important” docs — a doc.type is checked first before doing all above stuff.

Perhaps, you have heard of the phrase:

Code is read more than it is written.

Check out this piece of beauty:

for (int i = 0; i < changes.size(); i++) {

Above code is written in an imperative style, which means that the concrete statements — which manipulate state and behaviour — are written out explicitly.

  • Initialize an int i with zero
  • Loop while int i is less then the size of the changes list
  • Increment int i with 1 each iteration

In this style of imperative (procedural) coding (which most of the mainstream languages, including object-oriented programming (OOP) languages, such as Java, C++, C#, were designed to primarily support) a developer writes the exact statements a computer needs to perform to accomplish a certain task.

A few signals of very imperative (procedural) code:

  1. Focus on how to perform the task
  2. State changes and order of execution is important
  3. Many loops and conditionals

The code clearly focuses on the “How” — which makes the “What” hard to determine.

Focus on the What

Our first step, as the title of this article already have away, is to move away from the imperative style of coding and refactor to a more declarative style — of which FP is a form.

The loop is bugging me the most.

Here’s the new version of the code.

class FeedHandler {

  Webservice webservice
  DocumentDb documentDb

  void handle(List<Doc> changes) {

    // for (int i = 0; i < changes.size(); i++) {
    //    def doc = changes[i]
    changes
      .findAll { doc -> doc.type == 'important' }
      .each { doc ->

      try {
        def resource = webservice.create(doc)
        doc.apiId = resource.id
        doc.status = 'processed'
      } catch (e) {
        doc.status = 'failed'
        doc.error = e.message
      }
      documentDb.update(doc)
    }
  }
}

What’s changed?

  • The if (doc.type == 'important') part has been replaced with a findAll { doc -&gt; doc.type == 'important' } again on the document collection itself — meaning “find all documents which are important and return a new collection with only those important documents”
  • The imperative for-loop (with the intermediate i variable) has been replaced by the declarative each method on the documents collection itself — meaning “execute the piece of code for each doc in the list and I don’t care how you do it” &#55357;&#56898;

Don’t worry about each and findAll: these methods are added by Groovy, which I use happily together with Java in the same code base, to any Collection, e.g. Set, List, Map. Vanilla Java 8 has equivalent mechanisms, such as forEach to iterate a collection more declaratively.

What leads to readable software is:

Describe “What” and not “How”.

I can easily see what’s going on if I write my code in a more functional style, which saves me time (because yes, I do read code 90% of the time instead of writing it) and writing it like this is less error-prone, because less lines gives less opportunity for bugs to hide.

This is it for now

In part 2, we will name things properly, paving the way for more functional programming, such as “Either” or “Try” even later in the series.

Published on Java Code Geeks with permission by Ted Vinke, partner at our JCG program. See the original article here: Functional Java by Example | Part 1 – From Imperative to Declarative

Opinions expressed by Java Code Geeks contributors are their own.

Ted Vinke

Ted is a Java software engineer with a passion for Web development and JVM languages and works for First8, a Java Web development company in the Netherlands.
Subscribe
Notify of
guest

This site uses Akismet to reduce spam. Learn how your comment data is processed.

1 Comment
Oldest
Newest Most Voted
Inline Feedbacks
View all comments
Ra2017
7 years ago

Informative! Loved the example!

Back to top button