Re: [proto] Hold terminals by "smart" reference
On 05/06/2012 20:38, Eric Niebler wrote: I want you to understand that I'm not just being obstructionist or obstinate. Proto's value functions are very simple and low-level and are called very frequently. Adding metaprogramming overhead there, as would be necessary for adding a customization point, has the potential to slow compiles down for everybody, as well as complicating the code, tests and docs. The change required to provide this feature is to replace the implementation of value from return e.proto_base().child0; to return e.proto_base().value(); and of course to change the specialization of (basic_)exprterm, 0> accordingly. That is all. I'm not sure this complicates the code, albeit for good measure it would be nice to avoid the use of the name proto_child0 for the type of the terminal, too. There are also unanswered questions. For instance, how does proto::matches work with these terminals? I'm not terribly familiar with how proto::matches works, but if it uses the proto_grammar typedef, then it could be made so that it wouldn't notice any difference. Does it match on the actual value or the logical one? There are arguments on both sides, but one needs to be picked. Going with the logical value will force proto::matches to go through this customization point for every terminal. I also am thinking about how it effects other proto features such as: as_expr, as_child, make_expr, unpack_expr, literal+lit, fusion integration, display_expr, fold and all the other transforms, etc. etc. I doubt any of these rely on specific implementation details of basic_expr, 0>, so they wouldn't be affected. Making proto's user's happy must be balanced against feature-creep-ism, which hurts everybody in the long run. So I'm afraid I'm still leaning against adding this customization point. No problem, I thought it would have been an interesting addition. ___ proto mailing list proto@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/proto
Re: [proto] Hold terminals by "smart" reference
On 6/4/2012 5:51 PM, Mathias Gaunard wrote: > On 04/06/2012 17:52, Eric Niebler wrote: > >> I don't know what you mean by the "right type". If you want it held by >> shared_ptr to manage lifetime, then shared_ptr is the right type, it >> seems to me. Or use a wrapper around a shared_ptr, whichever. > > I want all tree manipulation and transformation algorithms to see the > value as if it were a T and not a shared_ptr or ref_holder. OK, I see. > shared_ptr is the right type to contain the terminal in the proto > nullary expression, but in that particular case it is not the logical > type of the value associated to that leaf node. > > I want to be able to manipulate the tree using straight Proto tools > (otherwise I might as well not use Proto at all -- the point is to have > a well-defined de-facto standard framework for tree manipulation). I understand your frustration. > Those algorithms should not need to know how the value is stored in the > expressions. It is just noise as far as they're concerned. > > Alternatively I'll need to provide substitutes for value, > result_of::value and _value, and ban those from my code and the > programming interface, telling developers to use mybettervalue instead > of proto's. That saddens me a bit. I want you to understand that I'm not just being obstructionist or obstinate. Proto's value functions are very simple and low-level and are called very frequently. Adding metaprogramming overhead there, as would be necessary for adding a customization point, has the potential to slow compiles down for everybody, as well as complicating the code, tests and docs. There are also unanswered questions. For instance, how does proto::matches work with these terminals? Does it match on the actual value or the logical one? There are arguments on both sides, but one needs to be picked. Going with the logical value will force proto::matches to go through this customization point for every terminal. I also am thinking about how it effects other proto features such as: as_expr, as_child, make_expr, unpack_expr, literal+lit, fusion integration, display_expr, fold and all the other transforms, etc. etc. I worry that allowing the logical type of a terminal to differ from the actual type opens a Pandora's box of tough question with no obvious answers, and trying to add this would cause unforeseen ripple effects through the code. It makes me very uneasy, especially considering the workaround on your end (sorry) is very simple. Making proto's user's happy must be balanced against feature-creep-ism, which hurts everybody in the long run. So I'm afraid I'm still leaning against adding this customization point. But I encourage you to file a feature request, and if you can find a patch that doesn't negatively effect compile times or end user-complexity and integrates cleanly with all the other features of proto and has docs and tests, then -- and only then --- would I add it. -- Eric Niebler BoostPro Computing http://www.boostpro.com ___ proto mailing list proto@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/proto
Re: [proto] Hold terminals by "smart" reference
On 04/06/2012 17:52, Eric Niebler wrote: I don't know what you mean by the "right type". If you want it held by shared_ptr to manage lifetime, then shared_ptr is the right type, it seems to me. Or use a wrapper around a shared_ptr, whichever. I want all tree manipulation and transformation algorithms to see the value as if it were a T and not a shared_ptr or ref_holder. shared_ptr is the right type to contain the terminal in the proto nullary expression, but in that particular case it is not the logical type of the value associated to that leaf node. I want to be able to manipulate the tree using straight Proto tools (otherwise I might as well not use Proto at all -- the point is to have a well-defined de-facto standard framework for tree manipulation). Those algorithms should not need to know how the value is stored in the expressions. It is just noise as far as they're concerned. Alternatively I'll need to provide substitutes for value, result_of::value and _value, and ban those from my code and the programming interface, telling developers to use mybettervalue instead of proto's. That saddens me a bit. ___ proto mailing list proto@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/proto
Re: [proto] Hold terminals by "smart" reference
On 6/3/2012 5:37 PM, Mathias Gaunard wrote: > On 03/06/2012 18:36, Eric Niebler wrote: > >>> Plus I don't have a good way to distinguish between a terminal of >>> shared_ptr and a terminal of T which is held through a shared_ptr. >> >> Have you tried a grammar? Something like (untested) proto::terminal< >> boost::shared_ptr< proto::_> > ? > > That would match expressions of the form (assuming I have binary plus in > my grammar) > > shared_ptr p1, p2. > p1 + p2; I don't understand. p1 and p2 are not Proto terminals, so "p1 + p2" doesn't make sense. Even if it did, it would build a plus node which would *not* match the grammar I gave above. Let's back up. What are you trying to do? > This is exactly what I do not want. I don't want my grammar to be > cluttered by implementation details. It makes no sense semantically for > shared_ptr to be values, it's just a technique used for life time > management of specific values. > > If I ever introduced shared_ptrs as values in my grammar, they might do > something entirely different. OK. If you want to hide the use of shared_ptr, I suggest writing a custom wrapper class named, say, my_detail::by_ref_holder which stores a shared_ptr as a data member. You can then choose how you want to handle terminals of this type. > To separate this more or less cleanly, I use a special tag for nullary > expressions where shared_ptr is just an implementation detail, but it's > still not really satisfying since the value doesn't have the right type > in the tree. I don't know what you mean by the "right type". If you want it held by shared_ptr to manage lifetime, then shared_ptr is the right type, it seems to me. Or use a wrapper around a shared_ptr, whichever. -- Eric Niebler BoostPro Computing http://www.boostpro.com ___ proto mailing list proto@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/proto
Re: [proto] Hold terminals by "smart" reference
On 03/06/2012 18:36, Eric Niebler wrote: Plus I don't have a good way to distinguish between a terminal of shared_ptr and a terminal of T which is held through a shared_ptr. Have you tried a grammar? Something like (untested) proto::terminal< boost::shared_ptr< proto::_> > ? That would match expressions of the form (assuming I have binary plus in my grammar) shared_ptr p1, p2. p1 + p2; This is exactly what I do not want. I don't want my grammar to be cluttered by implementation details. It makes no sense semantically for shared_ptr to be values, it's just a technique used for life time management of specific values. If I ever introduced shared_ptrs as values in my grammar, they might do something entirely different. To separate this more or less cleanly, I use a special tag for nullary expressions where shared_ptr is just an implementation detail, but it's still not really satisfying since the value doesn't have the right type in the tree. ___ proto mailing list proto@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/proto
Re: [proto] Hold terminals by "smart" reference
On 6/3/2012 6:23 AM, Mathias Gaunard wrote: > On 03/06/2012 02:59, Eric Niebler wrote: > >> There is no way to hook proto::value to return anything but what is >> stored in the terminal. It's a very dumb, low-level function. You could >> easily define your own value function that does something smarter, tho. > > I'm currently doing it with my own function, but that means I need to > use my own value instead of Proto's everywhere (value, result_of::value, > or _value). Right. > Plus I don't have a good way to distinguish between a terminal of > shared_ptr and a terminal of T which is held through a shared_ptr. Have you tried a grammar? Something like (untested) proto::terminal< boost::shared_ptr< proto::_ > > ? > I was considering specializing something like expr term_shared, 0> and basic_expr, 0> to do > this, but it appears I also need to change proto::value itself to call a > function instead of returning child0 directly. In my opinion, defining your own value function would be a much easier, cleaner solution. -- Eric Niebler BoostPro Computing http://www.boostpro.com ___ proto mailing list proto@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/proto
Re: [proto] Hold terminals by "smart" reference
On 03/06/2012 02:59, Eric Niebler wrote: There is no way to hook proto::value to return anything but what is stored in the terminal. It's a very dumb, low-level function. You could easily define your own value function that does something smarter, tho. I'm currently doing it with my own function, but that means I need to use my own value instead of Proto's everywhere (value, result_of::value, or _value). Plus I don't have a good way to distinguish between a terminal of shared_ptr and a terminal of T which is held through a shared_ptr. I was considering specializing something like exprterm_shared, 0> and basic_expr, 0> to do this, but it appears I also need to change proto::value itself to call a function instead of returning child0 directly. ___ proto mailing list proto@lists.boost.org http://lists.boost.org/mailman/listinfo.cgi/proto