
OCaml 4.03: Everything else - yminsky
https://blogs.janestreet.com/ocaml-4-03-everything-else/
======
melling
I recently started to learn OCaml. This blog post convinced me that it was
worth learning:

[http://roscidus.com/blog/blog/2014/02/13/ocaml-what-you-
gain...](http://roscidus.com/blog/blog/2014/02/13/ocaml-what-you-gain/)

I'm putting my notes on github, in case anyone wants a head start.

[https://github.com/melling/ComputerLanguages/blob/master/oca...](https://github.com/melling/ComputerLanguages/blob/master/ocaml.org)

------
GreaterFool
I really hope modular implicits will make it to the language one day. While
OCaml libraries are no stranger to monads they usually only include `bind` and
`return`.

Since I'm coming from Haskell I'm used to a vast Applicative and Monad
vocabulary and making do with just `bind` and `return` is rather painful. So
having a generic library of Monad combinators that one could use with any
Monad would be great. Also, being able to just write `show x` is so nice!

Edit: while I often see "modular implicits are being worked on" it is not very
clear whether there is a concrete plan to add them to the language. Is there
any place in the official OCaml repository / issue tracking system / wiki etc
where one could check the status?

~~~
massysett
"monads they usually only include `bind` and `return`"

All you need for a monad is `bind` and `return`. Is the problem that there are
not polymorphic monad combinators like `sequence`, `traverse`, etc.?

~~~
lmm
Yes. You can implement sequence/traverse/etc. for each specific monad in
OCaml, but if you want to write a generic implementation that will work for
any monad then you need typeclass-like functionality.

~~~
nv-vn
Not necessarily. You can manually pass in the module for the monad using
first-class modules and then define the functions in terms of that. You could
also define those operations in terms of monads using a functor if you want it
to look more like Haskell.

------
e_d_g_a_r
For anyone looking for an OCaml quick start: [http://hyegar.com/2015/10/20/so-
youre-learning-ocaml/index.h...](http://hyegar.com/2015/10/20/so-youre-
learning-ocaml/index.html)

------
xvilka
And here is the pending effort for better experience of OCaml on Windows:
[https://github.com/ocaml/opam/issues/2191](https://github.com/ocaml/opam/issues/2191)

~~~
kevingadd
Getting OCaml working at all on Windows was a hell nightmare early last year
when we were setting it up for WebAssembly and that definitely soured people's
opinions of it. We stuck with it because it had some dedicated fans in the
working group (happily using it on linux, mostly) and it turned out to be
worth the trouble, but otherwise we would have turned to some other language
(F#, probably). So I'm really glad to see those problems are being taken
seriously!

~~~
pjmlp
I for one was quite disappointed to have bought the book "Real World OCaml"
only to notice that it wasn't supported on Windows.

So aside a short gig to port old Caml Light code that I had lying around into
OCaml, I actually spend my ML like coding in F#.

~~~
systems
why did you buy the book, you can read it free online

~~~
baldfat
I usually buy online books to support the project. Not the person who bought
this book.

~~~
pjmlp
Same with me.

Sure I was disappointed, but sponsoring the people working on OCaml is more
important.

------
BWStearns
If I were already sold on using Haskell or OCaml for a new project, what would
be the big seller for OCaml being the choice? I haven't dug into SML or OCaml
and I'm not expert with Haskell yet but from looking at them they don't _look_
substantially distant from Haskell.

~~~
seagreen
I've only written Haskell, but I'll try to give a fair shakedown from my
perspective:

\+ OCaml is eagerly evaluated while Haskell is lazily evaluated. This makes it
easier to reason about things like memory use in OCaml.

\+ IO is reflected in the type signature of Haskell functions. You may find
this annoying because it stinks to have to change a lot of type signatures
just because, e.g., you want one of your utility functions to make a log entry
when called.

On the other hand, IO is often a huge deal either semantically or from a
performance perspective. For big projects having IO reflected in the type
system can be a huge help.

\+ The ecosystems are different. Haskell's is bigger, though I've heard the
quality of OCaml libraries tends to be very high.

~~~
mercurial
> IO is reflected in the type signature of Haskell functions.

What you mean is, "effects are reflected". Haskell has a monadic effect system
(IO is very rough-grained part of it), which can be combined via monadic
transformers.

Situations where you don't want to use OCaml:

\- you need good parallelism and using multiple processes are not enough
(concurrency is fine, though)

\- you want a large pool of developers (also applies to Haskell, but less so)

\- you like monadic effect systems

\- you need a number of libraries which are not present in the OCaml ecosystem

\- you want a build system that doesn't suck

\- you want a good standard library

\- you want typeclasses

Why you'd want to use OCaml over Haskell:

\- fast compilation (especially if you compile to bytecode)

\- no monadic effect system

\- no awful, ridiculous record field name collisions (OCaml lets you have two
distinct types with an "id" field, imagine that)

\- best-in-class package manager

\- faster than Haskell (I think?)

\- eagerly evaluated (Haskell's informal motto is "if it compiles it works",
complemented by "until you get a memory leak") and therefore makes it much
easier to reason about performance

\- high-quality ecosystem (though not always very well documented)

\- labeled arguments (many Haskell libraries have these functions with lots of
arguments which are quite confusing in the absence of labeled arguments)

\- great support for Vim/Emacs (IMHO, the Haskell equivalent to Merlin/ocp-
indent are not nearly as good, or at least were not as a few years ago)

\- great REPL via utop (just don't use the standard one, it's terrible)

\- an object system if you really need one

\- functors

\- pleasant "printf debugging" option, with a possibility of using a real
debugger if you need

~~~
catnaroek
What if I want some hybrid? From OCaml, I want the awesome module system and
strictness by default. (I'm not dismissing laziness or any other evaluation
strategy - just saying strictness is a better default.) From Haskell, I want
effects tracked in types, higher-kinded types and painless parallelism.

~~~
lmm
In order of less mainstream to more so

* Idris : modules?, strict by default, effect tracking by default, higher-kinded types, parallelism I think (at least on some platforms)

* Ceylon: modules, strictness, experimental higher-kinded types (possibly only on JS), parallelism (possibly only on Java)

* F#: modules, strict by default, parallelism

* Scala: some modularity, strict by default, higher-kinded types, parallelism

~~~
catnaroek
None of Idris, Ceylon or F# doesn't have ML-style modules:

(0) “In principle”, you could encode modules in Idris using dependent sum
types, but... Good luck with that! It isn't going to be terribly usable. In
general, Haskell and related languages don't consider it worth the effort to
give modules proper types. I guess we can be thankful Agda's modules don't
suck as badly as Haskell's - at least they can be nested.

(1) Ceylon and Scala's type systems are sophisticated enough to encode _some_
of the use cases for modules with objects, but invariably the result is
awkward. And other use cases are just impossible. For example, how should I
encode an ML functor that takes as arguments two modules with shared type
members? If it's possible at all, I don't even want to imagine how horrifying
it will be to manually turn all the sharing by fibration into sharing by
parameterization.

(2) F# doesn't allow any encoding of ML-style modules. Nothing. Nichts. Nada.
It's the only so-called “ML dialect” where the most important feature from ML
is completely missing.

~~~
nv-vn
You could encode a module as a record with a stored type and functions for it
for Idris. Then you can simply create functors as functions that take one type
of record in and return another type. The syntax is ugly, but you can define
macros to make it slightly more appealing. It's not an optimal approach
because of namespacing of record fields, but I remember hearing that one of
the next few Idris releases was going to change how record fields get
namespaces.

~~~
catnaroek
ML's module language has subtyping. Given any module signature, you can obtain
a supersignature by forgetting any of the following:

(0) The presence of a value component.

(1) The presence of a type component.

(2) The concrete definition of a type component, while still remembering its
presence.

I am not sure you can do this in Idris, other than manually shuffling data
between multiple dependent record types. Which is rather inconvenient: If you
have a module with 20 components, the last thing you want to do is manually
shift 15 of them to another module.

Also, unlike vanilla Haskell (no extensions) type classes, which can only have
a single type parameter, ML modules can have more than one type component.

------
catnaroek
Still no support for threads running in parallel? I guess things didn't go
well:
[https://news.ycombinator.com/item?id=9582980](https://news.ycombinator.com/item?id=9582980)

~~~
Scramblejams
There's still hope!

 _There are a number of much anticipated features that haven 't made it into
this release. In particular, the multicore GC, which at one point had been
expected to land in 4.03, has been pushed back, likely to 4.04._

~~~
zerosign
and when exactly 4.04 will pop up ?

~~ Well, I know, it's hard. ..

~~~
technomancy
I'm guessing after 4.03 and before 4.05?

------
doomrobo
Could anyone explain ephemerons further, maybe with examples? It seems really
interesting.

~~~
jlouis
The wikipedia page explains them pretty well I think, so going there is a
better explanation than anything else.

For a programmer, they allow you to be more precise about the point in time
where an object should be regarded as a weak object. That is, an object which
can be collected when under GC pressure. A weak references edges itself toward
this goal, but often require some manual intervention and/or knowledge of the
GC world to manage by the programmer. An ephemeron removes this additional
knowledge from the programmers mind. It allows one programmer to make an
interface which is truly not leaking in GC abstraction. So other programmers
don't have to know about it at all.

------
zerosign
how about SMT support for ocaml(multicore) ? Could it catch up to the current
implementation (HEAD) or it's still in the process of moving its
implementation ?

------
agentgt
I wonder if this change will have any impact on multicore OCaml (given the
reduction of allocation)? I don't know the internals of OCaml that well but
multicore support has been my BS reason for not embracing OCaml albeit Mirage
is looking better and better every day.

------
3327
Basically JaneStreet realized its a tough time maintaining the repo if they
are the only ones using it.

~~~
cies
Sure. Facebook? Bloomberg? Citrix?

[https://ocaml.org/learn/companies.html](https://ocaml.org/learn/companies.html)

