Enbugger
Enbugger

Reputation: 366

What is Java 8 functional way to implement switch-like construction without "switch" and "if" statements using only java.util

I wrote next code without using if statements and creating own functional API. And it checks some condition.

import java.util.*;

public class Test {
    public static void main(String[] args) {
        String smth = new Random().nextBoolean() ? "something" : null;

        Optional.ofNullable(smth)
                .filter(i -> !i.isEmpty())
                .<Runnable>map(i -> () -> System.out.println("Success " + i))
                .orElse(() -> System.out.println("error"))
                .run();
    }
}

How can I implement switch statement using only java.util.*?

Upvotes: 1

Views: 2368

Answers (3)

Kot Leapold
Kot Leapold

Reputation: 47

JMPL is simple java library, which could emulate some of the features pattern matching, using Java 8 features. This library support many patterns, which could see in many languages, such C#, Scala, Rust, Swift.

    matches(data).as(
      new Person("man"),    () ->  System.out.println("man");
      new Person("woman"),  () ->  System.out.println("woman");
      new Person("child"),  () ->  System.out.println("child");        
      Null.class,           () ->  System.out.println("Null value "),
      Else.class,           () ->  System.out.println("Default value: " + data)
   );


   matches(data).as(
      Integer.class, i  -> { System.out.println(i * i); },
      Byte.class,    b  -> { System.out.println(b * b); },
      Long.class,    l  -> { System.out.println(l * l); },
      String.class,  s  -> { System.out.println(s * s); },
      Null.class,    () -> { System.out.println("Null value "); },
      Else.class,    () -> { System.out.println("Default value: " + data); }
   );

   matches(figure).as(
      Rectangle.class, (int w, int h) -> System.out.println("square: " + (w * h)),
      Circle.class,    (int r)        -> System.out.println("square: " + (2 * Math.PI * r)),
      Else.class,      ()             -> System.out.println("Default square: " + 0)
   );

Upvotes: 1

Joop Eggen
Joop Eggen

Reputation: 109567

Simplistic:

new Runnable[] {
    () -> System.out.println("0"),
    () -> System.out.println("1"),
    () -> System.out.println("2")
}[i].run();

Already useful:

Map<String, Runnable> map = ImmutableMap.<String, Runnable>builder()
    .put("0", () -> System.out.println("0"))
    .put("1", () -> System.out.println("1"))
    .build();
map.getOrDefault("2", () -> System.out.println("rest")).run();

However for playing with functional style programming, better try a really functional programming language.

Upvotes: 3

lesz3k
lesz3k

Reputation: 158

In functional programming there's a tight relationship with pattern matching and I guess that you want to achieve exactly that. As of this moment, such feature is not supported out of the box with the standard Java 8. It is, however already debated how it could be implemented in the future - have a look at the document from Brian Goetz.

In the meantime you could have a look at this blog, it utilizes VAVR, a library that facilitates pattern matching. So in your case it would look like this:

import java.util.*;

public class Test {
    public static void main(String[] args) {
        String smth = new Random().nextBoolean() ? "something" : null;

        String result = Match(smth).of(
            Case($(isNull()), "Success " + smth), 
            Case($(isNotNull()), "error"));
    }
}

Upvotes: 1

Related Questions