GADTs are not for a newcomer audience though. If you want to use GADTs you should be able to read the relatively short manual chapter that explains them.
I don’t know what you’re referring to by ‘the accumulator trick’.
GADTs are not for a newcomer audience though. If you want to use GADTs you should be able to read the relatively short manual chapter that explains them.
I don’t know what you’re referring to by ‘the accumulator trick’.
I disagree. Even if its not going to be needed by most beginners, this does not means that the documentation could not be improved.
Metaclasses in Python are not the first thing users need when they start using the language, but when the time come, they can find documentation explaining it, without requiring them to follow a master class.
Have a look at the reference to the word accumulator in this page
I think this “accumulator trick” is seen as a functional programming/algorithms concept, not as part of the “language”, and therefore out of scope for the language manual, but in scope for an ocaml focused programming book.
I think more example for GADT is definitely worthy of a PR to GitHub - ocaml/ocaml: The core OCaml system: compilers, runtime system, base libraries (I am not a maintainer here, they might disagree, but I don’t see a reason they would).
The accumulator pattern would probably be best served as a tutorial page on ocaml.org, I am not sure how to do it, but the maintainers at GitHub - ocaml/ocaml.org: The official OCaml website. certainly would.
Yeah sorry, I think I made too big a generalization with “culture of documentation”. Debating which language has more docs is not a productive discussion, since, as you correctly pointed out, we can always pick and point at various libraries. However, I do think regardless of the language, documentation is something to always be improved. Rust certainly could do more in this area. docs.rs is nice, but it often leans more towards an API reference instead of providing examples.
Earlier I pointed to the standard library page which mentioned examples near the very beginning of the page. If people don’t read the first few lines of the page, what can be done?
A lot actually! People don’t read docs linearly. They scan and look for examples. We can bemoan this and tell them to RTFM, or we can accommodate them and put examples first and add more of them. Specifically, with In_channel
, it’s not even clear that this module is for reading files. Like the description is “This module provides functions for working with input channels.”. If I were reading this and didn’t have prior knowledge that this is how OCaml handles files, I would skip over this page entirely. That’s why putting the examples first is a good idea. Users can see “oh, this is for reading files”.
Really the issue here is naming. In_channel
is an extremely vague name. If I write fs::
in my editor, the autocomplete will show me fs::read
, fs::read_to_string
, etc. If I search in Rust’s standard library for “read”, then I get fs::read
immediately. And when I attempt to recall the API for reading a file, it’s very easy to remember. Will I remember In_channel.with_open_bin file In_channel.input_all
? No, probably not. Maybe after a few dozen times, but not immediately.
You may counter that this is a relatively minor issue. Just learn the specific API and move on. But this is what creates the first impressions that ultimately determine whether someone sticks with a language. If they try to read a file, and parse out some data, but they get stuck because it’s not clear how to read a file in the OCaml tutorial (which btw this should really be in the Tour of OCaml), then they have to search around a bunch, eventually get directed to In_channel
but it’s sort of confusing because what do channels have to do with files, and eventually they figure out ok it’s this incantation that I have to memorize, well they’re going to leave the language feeling exhausted and like it’s not friendly enough to do easy tasks. Whereas if the API is simple, the docs have a plethora of examples, and the naming makes sense, they’ll leave thinking “huh, that was kind of easy, maybe I’ll write something else with this language”. It’s like this xkcd comic. You gotta make the language feel like you’re flying.
True enough but this goes back to “who is the audience?”. OCaml is very unix-oriented in a way. “File” can mean various things, including directory and socket. channel
could have been “stream” etc. For newbies with no programming experience at all “file” means one thing; for experienced programmers new to OCaml, something else. as always this boils down to “so much to do, so little time”. Rank newbies need special care and feeding, but who has the time and energy to write those docs?
Then again, In_channel
seems to be exclusive to regular files. OCaml is old; full of names that, w the benefit of hindsight, could have been better.
This is constructive, helpful, feedback! Someone should really open an issue or even better send a PR. Eg it would be great if the In_channel
doc page’s first line was something like ‘Buffered input from files’, and the corresponding change for the Out_channel
doc too.
Thank you @NicholasLYang for your contributions to this thread. I just want to remind that the documentation situation in OCaml is, from my point of view, improving significantly in recent times.
If you like to watch videos you can also take a look to https://watch.ocaml.org/.
I agree that some names in libraries/module is a bit surprising at the beginning, and it is something always a matter of debate (in_channel? streams? etc…), but as other commented the initial orientation was probably unix (see ocaml-unix) and eventually you get used to the conventions of each language. OCaml has almost 30 years old, so comparing with Rust (about 13 years old) would have obviously friction points regarding stdlib decisions. Probably, users coming from Python3 would find strange all the functions of Printf module, but those who are coming from C may understand some decisions better (man 3 printf
). Yes, I agree that In_channel
and Out_channel
doc could be improved for beginners.
Certainly! Even in my limited experience with OCaml, I’ve noticed that the quality and quantity of documentation has improved drastically. Kudos to everyone who has worked on this.
I also don’t want to just be a critic here. My goal is to help OCaml and grow the community. I truly believe OCaml could be 100x more popular. It’s a really great language and genuinely fun to write. Rust owes its existence to OCaml, so it’s only fair that perhaps the Rust community should contribute back.
As for the Unix-isms in the standard library, I understand that may be why the standard library has some unusual naming, but I do think it should be a priority to create a more uniform, user friendly standard library with better documentation. Perhaps that could be an initiative? Otherwise this does seriously hamper OCaml’s appeal towards beginners.
I tend to agree with this. It’s been mentioned elsewhere, but there are almost always better ways to spell simple things without GADTs. If you want to codify some more unusual invariants into the type system or get finer granularity than normal types give you, then GADTs can serve that purpose, but you’ll know it when you need it.
On the other hand, my first exposure to GADTs was through Haskell. Despite the fact that this feature is hidden behind a compiler extension there, it’s a more natural fit because variant and type constructors are “just functions” (in the term or type planes, respectively), so it’s easier to see exactly how GADTs differ from garden variety ADTs. Specifically, they’re a generalization in the sense that they allow you to return a refined type based on the data constructor you use (that is, they sit somewhere between data functions and type functions). The funny thing is that I think the OCaml manual does a better job of explaining this than the Haskell Wiki.
It works the same way in OCaml too:
# type t =
| A : t
| B : t;;
type t = A : t | B : t
Just curious, have you had a look at Jane Street’s “standard libraries”? For example, Jane Street’s stdio
library has pretty decent documentation, e.g. the one-liner for In_channel
makes it pretty clear that the module is for reading files:
An input channel for doing blocking reads from input sources like files and sockets.
And reading a whole file is as simple as that:
In_channel.read_all filename
More generally, I feel that 80% of the complaints I hear about OCaml just go away when you simply use Jane Street’s libraries. Not sure why not more people do (and advertize doing) just that…
As far as the standard library shipped with the compiler is concerned: given the long history, need to provide backward compatibility, and lack of benevolent dictator, expecting a coherent, fine-tuned naming scheme and design philosophy is probably and sadly an uphill battle.
Tbh, Jane Street libraries documentation is also pretty spotty. There are many modules that are just type signatures.
Regarding the standard library, it’s now proven that they are accepting improvements big and small. There have been many over the past few years. Imho the impediment now is not so much the historical reasons, and more that people quietly go away once you ask them to send a PR.
Tbh, Jane Street libraries documentation is also pretty spotty. There are many modules that are just type signatures.
Care to provide an example? I think your view may be outdated, or perhaps you are referring to some of the more niche modules/libraries?
I agree with your other points and I’m all for improving the standard library. Though I do wonder, why not just use and recommend Jane Streets libraries instead?
One of the big strengths of Jane Street’s libraries is a very consistent design philosophy and naming scheme, and a sometimes opinionated design. To a first approximation, if you know how to use one JS module, you know how to use any JS module. I think that achieving this is much easier when power/ownership/culture is highly concentrated, and when you’re willing to make breaking changes. OCaml’s standard library naturally has a lot more cooks in the kitchen, and different contributors have different ideas about what’s best.
It seems to me that the OCaml community largely rejects the “move fast and break things” culture, and that’s one reason I like it. Reportedly the Haskell community is just the opposite, gleefully breaking things left and right in search of The Perfect API, and I hope OCaml won’t fall into the same trap.
I have, yes. I’ve been learning OCaml using the Real World OCaml book, which uses them. However, unless the Jane Street libraries become the de facto, universally recommended standard, I think there’s still merit to improving the OCaml standard library. It is what most users will encounter and what is often referenced in answers online.
Also, even with the good documentation, I still believe In_channel
is just not an ideal name for files. Now, this is significantly better because it’s in a stdio
package and the aforementioned documentation, but it still is not necessarily easy to find due to the naming.
Let me ask you a related but more concrete question–is OCaml Stdlib documentation more spotty than Jane Street Base library documentation? Like if you go browse a random selection of modules of both, do you find that the standard library documentation is more bare ie more type signatures than actual documentation? Can you provide examples?
Eg:
vs
The day you have a problem you report an issue or open a PR, it gets a tag labelled forwarded-to-js-devs
and it seems most of the time you never hear anything back.
Personally wouldn’t put myself in the dependency cone of JaneStreet, they follow their needs – which is of course a perfectly reasonable thing for them to do but those are opaque and not necessarily aligned with yours.
It’s a routine code dump approach to open source which I personally don’t find very healthy to depend on.
More generally I feel that 90% of the complaints I hear about OCaml just go away when I simply use my stuff :–)
Regarding all these criticisms of the OCaml standard library.
It seems a common thing, not only in OCaml but in programming in general, to criticize a whole standard library of a language when several functions or a specific module does not please us or we think it could be otherwise. In other words, the OCaml standard library is much more than In_channel
, or a specific module.
The standard library can be improved, I agree, but personally what I value most in a standard library is stability, battle-tested and a growing slow but steady. Better documentation, of course (I agree with @NicholasLYang on that), and I’m sure a PR is always welcome in that regard. Improvements in the standard library happen and are discussed (just look at examples of PR) but of course they require debate and consensus as we expect from an opensource standard library (and I don’t think that a benevolent dictator is a better option)
Remember that each user is absolutely free to use the -nostdlib -nopervasives
options in the compiler and use whatever they see fit better in their programs. Personally, I am a happy user the standard library which occasionally use other specific modules as @dbuenzli commented, but still for those that want to try alternatives this link can be useful.
Base and Core are good libraries, but I wouldn’t recommend them (if anybody cared to ask me )
Do you send the beginner in question straight to base without ever using the standard library? Then it means you are teaching them dependency management in OCaml before they are allowed to read a file.
Are you teaching them the standard library first before moving them to JS libs? It means you have to teach them 2 ways to create a Map.
I think using incompatible libs, is just too much upfront for a newcomer, and they would be much better served by starting with the standard library, and then moving to containers.