Boost logo

Boost :

From: Brian McNamara (lorgon_at_[hidden])
Date: 2003-10-30 21:19:49


On Fri, Oct 31, 2003 at 09:50:47AM +0800, Joel de Guzman wrote:
> be swayed. Here's my use-case:

This is good (I agree use-cases are better than "theory" here).

I don't quite understand all the details of your use-case, though.

> Spirit parsers return a thing called a match<T> that reports the
> success (or failure) of a parse. Each parser has an attribute (return
...
> Obviously, since a match<T> can be an unsuccessful match, it is best
> to implement T, internally, as an optional<T>. The match's attribute
...

I am ok so far...

> Now, consider a symbol-table parser. A symbol table has a slot T
> for each symbol (like a map). This data-slot T is mutable (like a map).
> A reference to this data-slot must be passed to the semantic action.
> Obviously, the data-slot should be passed by reference:
>
> void bar(int&);
>
> symbols<int> s;
> s = "hello", "world";
>
> r = s[bar];
>
> Here, we want *s* to return a match<T&>. We want it to act like a
> true reference so that we won't have to write special code for the
> handling of reference attributes. The match attribute handling
> code and the semantic action handling code does not care about the
> type of the attribute. It just passes the attribute to the semantic action
> transparently IFF the parse is successful.

I think I'm still with you...

> So my requirements is that a match<T&> must alias its source T. It
> would be uterly error-prone (silent, confusing and hard to debug) if
> somewhere, it is re-seated to reference another T:
>
> match<T> m(i);
> m.value(x); // ok, set the attribute to x
>
> match<T&> m(r);
> m.value(x); // NO, please don't reset the reference, that's not
> // what I want! references should only be set
> // *at construction time*. I want the thing referenced
> // by r set to x.

And now I'm lost.

Why doesn't this:

   template <class T>
   class match {
      optional<T> data;
      ...
   public:
      match( T x ) : data(x) {}
      ...
      void value( T y ) {
         *data = y;
      }
   };

do what you want? If T is a reference type, the match's constructor
puts the reference in the optional, and then calls to value() change the
value of the referred-to object. If T is a non-reference type, it also
works, as far as I can tell.

I am clearly missing something, but I don't know what. :)

-- 
-Brian McNamara (lorgon_at_[hidden])

Boost list run by bdawes at acm.org, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk