FunHop: Working with Exceptions in Scala – Problem Statement


If you look at the earlier posts in the FunHop series, you would notice that Exceptions are side effects. Exceptions by their very nature also break referential transparency and are context dependent. You would have got an idea about referential transparency from our earlier post. If not, it might be a good idea to review it once.

Let us consider the code sequence below

def fetchEmployeeName(id: Int) = {
    val z = throw new Exception("Employee not found")
    try {
      if (id > 0) "Jack" else z
    } catch {
      case ex: Exception => "John"
    }
  }

What would happen when we call this method with fetchEmployeeName(-1) ?

It would throw the exception “Exception in thread “main” java.lang.Exception: Employee not found”

Now, let us apply Referential Transparency to the above code. The new avatar of the code becomes

def fetchEmployeeName(id: Int) = {
    try {
      if (id > 0) "Jack" else throw new Exception("Employee not found")
    } catch {
      case ex: Exception => "John"
    }
  }def divide[A:Numeric](divident: A, divisor: A, div:(A,A)=>A): A = try {
    div(divident,divisor)
  } catch {
    case ex: Exception => 0
  }

What would be the output of fetchEmployeeName(-1) now? It would be “John”

Clearly exceptions are not referentially transparent. They are also context dependent. As you would notice in the above example, changing the context of the exception and bringing it inside the try block, changes the behavior of the logic.

Looking further, exceptions are also not Typesafe. Say for example if you look at the following piece of code

def divide(divident: Int, divisor: Int): Int = divident / divisor

The caller of this code, would in no way know that this code block could throw an exception. It would always assume that it would get back an Int value. In this way the Java Checked Exceptions were slightly better that the caller would know that it has to deal with an exception. Or at least it would know that there could be a scenario in which exception can be thrown.

So what is the option that we have?

One option is to define a Sentinel Value. It is a value which is returned when an error occurs so that the caller can take corrective action on the basis of that. So the code would become something like this

def divide(divident: Int, divisor: Int): Int = try{
   divident / divisor 
  }
  catch{
    case ex:Exception => 0
  }

Now how is this one better?

In this case, the caller of the method would always know that it is going to get back an Int, now matter what. It would never get back an exception. When it gets a “0” then it has to do some special handling. This has its own set of drawbacks. It results in boiler plate code on the caller side. Everytime, it would have to do some special handling. Also, it is not always possible to have a Sentinal Value. For example if we change our code to be polymorphic then what would you like to give as the value. Hence, our code becomes

def divide[A:Numeric](divident: A, divisor: A, div:(A,A)=>A): A = try {
    div(divident,divisor)
  } catch {
    case ex: Exception => 0
  }

This would not compile since we do not know what is the kind of A. All we know is that it is a numeric.

In the next post, we would look at how to handle exceptions better than the way we are handling them now.

Advertisements

About Vikas Hazrati

Vikas is the Founding Partner @ Knoldus which is a group of software industry veterans who have joined hands to add value to the art of software development. Knoldus does niche Reactive and Big Data product development on Scala, Spark and Functional Java. Knoldus has a strong focus on software craftsmanship which ensures high-quality software development. It partners with the best in the industry like Lightbend (Scala Ecosystem), Databricks (Spark Ecosystem), Confluent (Kafka) and Datastax (Cassandra). To know more, send a mail to hello@knoldus.com or visit www.knoldus.com
This entry was posted in Best Practices and tagged , . Bookmark the permalink.

2 Responses to FunHop: Working with Exceptions in Scala – Problem Statement

Leave a Reply

Fill in your details below or click an icon to log in:

WordPress.com Logo

You are commenting using your WordPress.com account. Log Out / Change )

Twitter picture

You are commenting using your Twitter account. Log Out / Change )

Facebook photo

You are commenting using your Facebook account. Log Out / Change )

Google+ photo

You are commenting using your Google+ account. Log Out / Change )

Connecting to %s