
OCaml mimicry in Java - PDoyle
https://engineering.vena.io/2016/05/30/ocaml-mimicry-in-java-jocaml/
======
jb9i
I translated the OCamel code to java with derive4j, takes <60 lines, took me
~15 mins:
[https://gist.github.com/jbgi/2d26c2b30b658ea84b3e458cc8e846a...](https://gist.github.com/jbgi/2d26c2b30b658ea84b3e458cc8e846aa)
Do not bother writing a "builder-generator" for algebraic data types: it
already exists:
[https://github.com/derive4j/derive4j](https://github.com/derive4j/derive4j)
;-)

------
CKloukinas
Don't know much OCaml (understatement...) but the way I understand it an OCaml
type-switch like the expr one is essentially enumerating the different ways
one can construct an expr. True is an expr, so is False, etc. - these are
constructors of expr not functions as I see it. So I'd code that in Java/C++
as a hierarchy that uses dynamic binding to achieve the case-specific
computation for the evaluation (since in OO, it's the compiler that should be
writing the switch'es) - in C++ [edit - some pointers don't render; all fields
are pointers to expr]:

struct expr { virtual bool eval() const = 0; }

struct True : public expr {bool eval() const {return true;}};

class Not : public expr { expr _exp; public: Not( const expr & e ) : exp( &e )
{} bool eval() const {return e->eval();} };

class And : public expr { expr _exp1, *exp2; public: And( const expr & e1,
const expr & e2 ) : exp1( &e1 ), exp2( &e2 ) {} bool eval() const {return
exp1->eval() && e2->eval();} };

And so forth. Different type constructors -> different sub-classes of the
abstract type. Functions operating on the type -> methods of the parent class,
that each sub-class overrides.

If instead of expr and True/False we had Shape and Triangle/Rectangle that
we're more used to looking as forming a hierarchy, it might make it easier to
see my point. Isn't this the Java/C++ way for doing so? If not, what am I
missing here?

~~~
PDoyle
You're right, that's the Java/C++ way. I was trying to do it the OCaml way in
Java. :-)

Ultimately, what I wanted was a way to declare the variants in one place. I
didn't want to repeat myself. The only way I could think of declaring them
once, and still being able to both produce and consume values of those types,
was with a generic visitor interface.

You've done it with a C++ class hierarchy, which has the following properties
that the OCaml solution does not:

First, it needs to repeat the components of each variant type three times:
once as field declarations, once as constructor arguments, and once as
initialization statements in the constructors. The OCaml one (and my Java one)
lets you declare the types, fields, and constructors in one line of code.

Second, your code is arranged into classes, which means that adding a new
function (say `toString`) requires adding new code in N places, for N types.
In OCaml, you'd just write one new function with N variants. (Of course, your
code is better if you want to add a new type.)

