Juha Nieminen <nos...@thanks.invalid> wrote:
> For a series of classes I'm making it would be nice if they had constructors
> that accept:
>
> - an interator range,
> - an initializer list, and
> - a variable amount of arguments (using a variadic template)
From a more hypothetical point, in theory it could be possible to
distinguish between an iterator range and a variable number of arguments
because in the latter case all the arguments have to be compatible with
the type accepted by the class. In other words, if you have something
like this:
template<typename Value_t>
class MyClass
{
public:
// All parameters have to be compatible with Value_t:
template<typename... Params>
MyClass(Params&&...);
// If two paramers are given and they are *not* compatible with
// Value_t, but *b and *e are compatible with Value_t, then this
// ought to be called:
template<typename InputIterator>
MyClass(InputIterator b, InputIterator e);
};
In principle if you give the constructor values of type Value_t (or anything
that's compatible with it, such as an object of a class derived from
Value_t, if Value_t is a pointer to an object), that's distinguishable
from two iterators which are not themselves compatible with Value_t, but
their dereferences are.
The standard library container classes usually do some template magic to
distinguish between integrals and iterator ranges. For example
std::vector<int> has a constructor that takes an iterator range and
another constructor that takes two integrals. If you call the constructor
with to ints, for example, it will match the iterator range constructor
(because it's a better match than the other constructor, which takes a
size_t and an int). However, std::vector still manages to do the right
thing, thanks to some template magic.
I was thinking that perhaps, possibly, the same kind of template trickery
could be used in this case.