|
Boost-Commit : |
Subject: [Boost-commit] svn:boost r83246 - sandbox/type_erasure/libs/type_erasure/doc
From: steven_at_[hidden]
Date: 2013-03-02 12:43:31
Author: steven_watanabe
Date: 2013-03-02 12:43:30 EST (Sat, 02 Mar 2013)
New Revision: 83246
URL: http://svn.boost.org/trac/boost/changeset/83246
Log:
Snip some sections.
Text files modified:
sandbox/type_erasure/libs/type_erasure/doc/type_erasure.qbk | 213 ---------------------------------------
1 files changed, 2 insertions(+), 211 deletions(-)
Modified: sandbox/type_erasure/libs/type_erasure/doc/type_erasure.qbk
==============================================================================
--- sandbox/type_erasure/libs/type_erasure/doc/type_erasure.qbk (original)
+++ sandbox/type_erasure/libs/type_erasure/doc/type_erasure.qbk 2013-03-02 12:43:30 EST (Sat, 02 Mar 2013)
@@ -415,214 +415,6 @@
[endsect]
-[section:design Design Notes]
-
-This section is purely for informational
-purposes. You don't need to read it to
-understand how to use the library. Here,
-I try to explain how the library evolved
-and why I chose the current interfaces.
-
-[section:concepts Concept Interfaces]
-
-When designing the concept system, I had a couple
-of goals. First of all, the basic definitions
-need to be simple. Second, concepts need to be
-composable. Making concepts composable is fairly
-easy by recursively expanding mpl sequences.
-The first goal is much harder. In earlier
-versions of TypeErasure and in most similar libraries
-such as DynamicAny and Adobe::Poly, the base
-definitions generally resemble the following
-
- struct incrementable_interface {
- virtual void increment() = 0;
- };
- template<class T>
- struct incrementable_implementation : incrementable_interface {
- virtual void increment() { ++x; }
- T x;
- };
-
- template<class Derived>
- struct incrementable_mixin {
- Derived& operater++();
- };
-
-Note that we require three definitions, the
-virtual interface, the virtual implementation,
-and the user level interface. In the immediate
-predecessor of this library, the first two
-were combined into a single template
-
- template<class T>
- struct incrementable :
- primitive_concept<incrementable<T>, void(T&) > {
- static void apply(T& t) { ++t; }
- };
-
-Here, the `primitive_concept` base specifies the
-function signature, serving the purpose of the
-virtual interface. We now have only one class
-here, but it's still excessively complicated.
-To get rid of this we can note that the signature
-must be `remove_pointer<decltype(&incrementable<T>::apply)>::type`
-and can therefore be deduced automatically.
-
-[endsect]
-
-[section:constructors Constructors]
-
-The constructors of __any have to serve three
-different purposes. First, we have constructors
-that capture the type passed. This is what
-happens when constructing an __any from an
-`int` for example. The second kind of constructor
-dispatches to a constructor of the contained
-type using an existing set of bindings. This
-is what happens for the copy constructor. The
-last kind of constructor "upcasts" from one
-concept to another more general
-concept. For example, `any< mpl::vector<copy_constructible<>, incrementable<> > >`
-should be convertible to `any<copy_constructible<> >`.
-We want to define these three kinds of constructors
-in an unambiguous way. For short, we'll refer
-to these three kinds of constructors an binding
-constructors, dispatched constructors, and
-converting constructors.
-
-# binding constructors take an argument
- which is the object to capture and
- an optional argument specifying any
- bindings that can't be deduced.
-# dispatched constructors take the
- arguments of the underlying constructor
- and an optional argument specifing
- the bindings to use. (This extra
- argument is needed when the bindings
- can't be deduced because none of
- the arguments is an any.)
-# converting constructors take an
- argument which must be an __any
- and an optional argument indicating
- how placeholders should be substituted.
-
-Now, where are the ambiguities?
-
-* A single argument which is not an __any
- can only match a binding constructor.
- It cannot match a dispatching constructor
- because we don't have anything to dispatch on.
- It can't match a converting constructor
- because it isn't an __any.
-* A single argument which is an __any can
- match all three. We'll rule out binding
- constructors by arbitrarily deciding that
- an __any can never contain another __any.
- This makes our job a lot easier. This
- leaves us with dispatched constructors
- vs. converting constructors. If the
- Concept of the argument is different
- from the Concept of the type being
- constructed, we have to have a converting
- constructor. If the concepts are the
- same and the placeholders are the same,
- then we have the copy constructor, and
- there is no difference between the
- dispatched constructor and the converting
- constructor. If the placeholders are
- different, then we call the dispatched
- constructor. In theory it's possible
- that this is intended to be converting constructor,
- but this is rare.
-* For two arguments, the converting and binding
- constructors take one argument that is either
- a __binding or a __static_binding. They
- can be distinguised by whether the other
- argument is an __any or not.
-
-We'll add one more requirement to avoid
-going crazy. No argument of a constructor
-to __any shall be __binding or __static_binding,
-except for the ones that are explicitly
-allowed.
-
-Now, we can at least allow users to explicily
-avoid any ambiguity with the following rules.
-
-# If there are exactly two arguments and the
- first argument is neither an __any nor a specialization
- of __binding or __static_binding, and the second
- argement is a specialization of __binding
- or __static_binding, then this is a binding
- constructor.
-# If the first argument is a specialization
- of __binding, then this is a dispatching
- constructor.
-# If there are exactly two arguments and the
- first argument is an __any and the second
- argument is a specialization of __binding
- or __static_binding, the constructor is
- a converting constructor.
-
-These are not ambiguous and any constructor
-call can be converted to one of these forms.
-Note in particular that the order of the
-arguments is important. If the *first*
-argument is a __binding, then we have a
-dispatched constructor. If the *second*
-argument is a __binding or a __static_binding,
-then we have either a binding constructor or
-a converting constructor.
-
-[endsect]
-
-[section:binding Binding]
-
-The easiest implementation of manual type erasure
-uses virtual functions. However, virtual functions
-are somewhat limited. We get a lot more flexibility
-by using explicit tables of function pointers.
-
-* A table can be constructed dynamically. This
- allows us to implement conversions by creating
- a subset of the table.
-* A table is easy to share between multiple types.
- This makes it easier to implement multi-type concepts
- and __any references.
-* A table can be passed around without a corresponding
- object. This allows us to implement captured constructor
- calls that don't take an __any argument.
-
-[endsect]
-
-[endsect]
-
-[section:feedback Feedback Wanted]
-
-There are a number of things that I'm not entirely
-happy about. Any thoughts about them would be
-greatly appreciated.
-
-* The name `_self`. Basically, I need some placeholder
- to act as a default. Since placeholders act as a
- substitute for template parameters, I'd really like
- to use `_T`. Alack-a-day, `_T` is a reserved identifier.
- `_self` was the best I could think of.
-* __relaxed_match. I considered a lot of names
- for this, `strict_match<false>`, `enable_mixed`,
- `nonstrict_match`, `loose_match`, `best_effort`,
- and probably more that I've forgotten. I'm not
- really happy with any of them. I'm not really
- happy about having it in `Concept` either, but
- I'm not sure where else it could go. It's presence
- can affect the contents of the vtable, so if it
- were a separate template argument, it would have
- to be passed to __binding as well. It would generally
- add complication.
-
-[endsect]
-
[section:future Future Work]
These are just some ideas. There is absolutely no
@@ -631,9 +423,8 @@
* Use SBO.
* Allow more control over vtable layout.
* Attempt to reuse sub-tables in conversions.
-* Allow "dynamic_cast".
-* Use C++0x features. (Rvalue references and
- variadic templates in particular.)
+* Allow "dynamic_cast". This requires creating
+ a global registry of concept mappings.
* Optimize the compile-time cost.
[endsect]
Boost-Commit list run by bdawes at acm.org, david.abrahams at rcn.com, gregod at cs.rpi.edu, cpdaniel at pacbell.net, john at johnmaddock.co.uk