caml-list - the Caml user's mailing list
 help / color / mirror / Atom feed
From: Gabriel Scherer <gabriel.scherer@gmail.com>
To: caml users <caml-list@inria.fr>
Subject: Re: [Caml-list] Odd failure to infer types
Date: Sun, 18 Sep 2011 09:26:32 +0200	[thread overview]
Message-ID: <CAPFanBF2Vpb9=4UNOX4Y-vpb4imW5VvKDGuwZmbvxU0Yk9X3cQ@mail.gmail.com> (raw)
In-Reply-To: <87bouj2wxv.fsf@frosties.localnet>

On Sat, Sep 17, 2011 at 2:08 PM, Goswin von Brederlow <goswin-v-b@web.de> wrote:
> I think you are missing the point.
>
> I totaly get why it must be '_a instead if 'a. My question is why it
> doesn't infer the full type from the call to the print function.

You're correct, I was missing your point. You have the following situation:

 let num_states =
  List.fold_left
    (fun num (sol, board) ->
      let d = D.get_all sol in
      let state = ([], sol, board)
      in
      Hashtbl.add cache board ();
      states.(d) <- state::states.(d);
      print state;
      num + 1)
    0
    G.solutions

with the following inferred types:
 states: ('_a list * (char * int * int) array * string) list array
 print: (int * int * dir) list * (char * int * int) array * string -> unit

(Remark: the types given above are the result of calling
"caml-types-show-type" in an Emacs buffer, after compiling the fail
with -annot; we get partial type information even when the compilation
fail)

Why doesn't the type of "states" get inferred from the call to `print state`?
The reason why is that `state`, contrarily to `states`, is
polymorphic. It has type (caml-types...) 'b list * (char * int * int)
array * string, because the empty list [] has polymorphic type.
Therefore, it can be used in two different contexts with *different*
types (instantiations) that don't get unified with each other
 states.(d) <- state::states.(d);
 print state;
on the first line, the type 'b list of [] is instantiated to a fresh
type then unified with the '_a list of states, and on the second line
it is instantiated again, independently, and the resulting fresh type
is unified with (int * int * dir) list.

You can see that this is the problem by forcing the list to have a
monomorphic type:
 let mono_list = ref [] in
 let state = (!mono_list, sol, board)
With this (indeed unreadable) version, your whole code compiles fine.
Another technique to do that would be:
 print (List.hd states.(d));

(I would still rather use a type annotation on the 'states' variable)

      reply	other threads:[~2011-09-18  7:27 UTC|newest]

Thread overview: 10+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2011-09-03  9:53 Goswin von Brederlow
2011-09-03 10:31 ` Christophe Papazian
2011-09-03 11:42   ` Guillaume Yziquel
2011-09-03 10:36 ` Guillaume Yziquel
2011-09-03 11:35   ` Philippe Veber
2011-09-03 11:46     ` Guillaume Yziquel
2011-09-03 12:15       ` Gabriel Scherer
2011-09-03 12:50         ` Guillaume Yziquel
2011-09-17 12:08         ` Goswin von Brederlow
2011-09-18  7:26           ` Gabriel Scherer [this message]

Reply instructions:

You may reply publicly to this message via plain-text email
using any one of the following methods:

* Save the following mbox file, import it into your mail client,
  and reply-to-all from there: mbox

  Avoid top-posting and favor interleaved quoting:
  https://en.wikipedia.org/wiki/Posting_style#Interleaved_style

* Reply using the --to, --cc, and --in-reply-to
  switches of git-send-email(1):

  git send-email \
    --in-reply-to='CAPFanBF2Vpb9=4UNOX4Y-vpb4imW5VvKDGuwZmbvxU0Yk9X3cQ@mail.gmail.com' \
    --to=gabriel.scherer@gmail.com \
    --cc=caml-list@inria.fr \
    /path/to/YOUR_REPLY

  https://kernel.org/pub/software/scm/git/docs/git-send-email.html

* If your mail client supports setting the In-Reply-To header
  via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line before the message body.
This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).