
On 09/20/10 13:56, dherring@ll.mit.edu wrote:
On Mon, 20 Sep 2010, Larry Evans wrote:
On 09/20/10 10:50, dherring@ll.mit.edu wrote:
See http://www.boost.org/doc/libs/1_44_0/doc/html/variant/design.html
In particular, "Temporary Heap Backup" and "Future Direction".
We have some specialized requirements. We couldn't even use boost::shared_ptr until it added both the custom allocator and deleter. The "never-empty guarantee" conflicts with our needs and is not a concern at this time.
An alternative to boost::variant is the:
http://svn.boost.org/svn/boost/sandbox/variadic_templates /boost/composite_storage/pack/container_one_of_maybe.hpp
which *might* work for you. I say *might* because I don't know exactly what you mean by:
"never-empty guarantee" conflicts with our needs
because those needs are not spelled out.
Rephrase: We don't need the never-empty guarantee; but it conflicts with the always-in-place requirement. Steven's suggestion to add boost::blank looks promising. The documentation should be updated to mention it.
I'm still unsure what "always-in-place" means. Based on what Steven was saying, I'm guessing it means only stack or static storage can be used (i.e. no calls to new or malloc). Is that right? If so, then one_of_maybe satisfies that requirement. However, unlike boost::variant, it makes no provision for failure of operator= when the source and target are different types; however, that could be remedied by simply catching any throw and setting which() to indicate the one_of_maybe was uninitialized. Since the uninitialized value ( of type nothing, defined here: http://svn.boost.org/svn/boost/sandbox/variadic_templates/boost /composite_storage/special_components.hpp ) cannot throw during construction, it would workaround the operator= problem.
This container looks interesting; but other than the sources, I don't see any documentation?
Will work on that ;)
For now, we'll stick with what I've cobbled together.
As a side note, we also must expose both the type of the "which" and the discriminant to member mapping (which may be N:1; see the CORBA IDL spec). So I believe boost::variant would still be hard to use even if the heap issue were resolved.
I'm also unsure of what's meant by:
the discriminant to member mapping (which may be N:1).
If you mean types could be duplicated, IOW, allow:
variant<int,int>
then that's what one_of_maybe does.
The one place I found for corba spec (found with google "corba idl spec") was here:
If you're interested, see also Part 1, section 7.11.2.2 of http://www.omg.org/spec/CORBA/3.1/ and the C++ mapping on http://www.omg.org/technology/documents/idl2x_spec_catalog.htm
We support a slight variant of this spec.
This layout (discriminant followed by dependent value) is the exact reverse of the container_one_of_maybe is laid out. Originally, the discrimiant was 1st; however, the following post:
That order doesn't bother me too much. The "N:1" notation meant that, just like a "switch statement", there may be N cases that specify one member. It is also possible for multiple members to have the same type.
[snip] This is what I meant to imply by the example: variant<int,int> With the current variant, this won't work; however, it's perfectly OK with one_of_maybe. One reason I wanted this was to emulate the way lex works, which returns a discriminated union. Most of the types in the union are simply unused because one's not really interested in the character string representation of some keyword, instead, one is only interested in which keyword was found, and that's encoded in the discriminant. One_of_maybe has another special type for this very purpose. It takes up no room (there's a specialization of size_of template which returns 0 for this special type); hence, it doesn't contribute to the calculation of the size of one_of_maybe.
Later, Daniel
Regards, Larry