caml-list - the Caml user's mailing list
 help / color / mirror / Atom feed
From: Jacques Garrigue <garrigue@math.nagoya-u.ac.jp>
To: cstork@ics.uci.edu
Cc: caml-list@inria.fr
Subject: Re: [Caml-list] Unquantifiable escaping type in variation of visitor pattern
Date: Wed, 09 Feb 2005 10:53:50 +0900 (JST)	[thread overview]
Message-ID: <20050209.105350.108297361.garrigue@math.nagoya-u.ac.jp> (raw)
In-Reply-To: <20050208225542.GA20967@anthony.ics.uci.edu>

From: Christian Stork <cstork@ics.uci.edu>

> I'm tying to implement a framework for visitors over trees (e.g. ASTs).
> These trees are built according to some rules.  Rules are much like the
> productions of a grammar.

In general I would advice against using an object-oriented
representation for ASTs. Variant types are the proven approach to do
that in functional languages, and generally work much better.

> The following minimal example demonstrates my current design problem:
[...]
> The above code has one special twist, it allows the visitor's visit...
> methods to hand eachother some argument, called the baton.  Different
> visitors might want to use different types of batons.  The above code
> tries to support this by parametrizing the accept method and the
> visitor class.  Sadly, Ocaml complains about then with 

This specific typing problem can be solved.
It stems from the fact you are defining someRule and ['baton] visitor
simultaneously, but use 'baton polymorphically in someRule.
Inside mutual recursive definitions of classes, parameters cannot be
used polymorphically.
The way to a void this problem is to break the recursion.
The following code does what you want.

type 'rule node = { rule:'rule; kids:'rule node list } 

class type ['baton,'rule] visitor = object
  method visitSomeRuleNode : 'rule node -> 'baton -> 'baton
end

class someRule =
  object (self)
    method accept
      : 'baton . someRule node -> ('baton,someRule) visitor -> 'baton -> 'baton
      = fun n v b -> v#visitSomeRuleNode n b
  end

class ['baton] visitor_impl =
  object (self)
    method visitSomeRuleNode n (b : 'baton) =
      List.fold_left
        (fun b' k -> (k.rule : someRule)#accept k (self :> _ visitor_impl) b')
        b n.kids
  end

Jacques Garrigue


      parent reply	other threads:[~2005-02-09  1:54 UTC|newest]

Thread overview: 8+ messages / expand[flat|nested]  mbox.gz  Atom feed  top
2005-02-08 22:55 Christian Stork
2005-02-09  0:16 ` [Caml-list] " John Prevost
2005-02-22 17:29   ` Christian Stork
2005-02-23  3:08     ` Jacques Garrigue
2005-02-24 12:16       ` Christian Stork
2005-02-24 23:57         ` Jacques Garrigue
2005-02-25  0:30         ` Jacques Garrigue
2005-02-09  1:53 ` Jacques Garrigue [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=20050209.105350.108297361.garrigue@math.nagoya-u.ac.jp \
    --to=garrigue@math.nagoya-u.ac.jp \
    --cc=caml-list@inria.fr \
    --cc=cstork@ics.uci.edu \
    /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).