8

I have two classes A and B, and an implicit conversion operator exists to go from one to the other, so that:

A a;
B b;
b = a; // Works

Is there a standard way to convert a std::list<A> to a std::list<B> ? (Or even from std::vector<A> to a std::list<B>).

I know I can iterate trough to the list and build the second list item by item, but I wonder if there is a more elegant solution.

Unfortunately I cannot use boost but out of curiosity as a bonus question, if boost can handle this, I'd be happy to know how too.

ereOn
  • 53,676
  • 39
  • 161
  • 238

1 Answers1

15

Well, yes. Each sequence container type has a template constructor that takes a pair of iterators (an iterator range) as an input. It can be used to construct one sequence from another, regardless of the sequence types, as long as the sequence element types are convertible to each other. Like for example

std::vector<A> v;
...
std::list<B> l(v.begin(), v.end());

Also sequence containers have assign member function which does the same thing with assignment semantics (as opposed to initialization semantics).

std::vector<A> v;
std::list<B> l;
...
l.assign(v.begin(), v.end()); // replaces the contents of `l`
AnT stands with Russia
  • 312,472
  • 42
  • 525
  • 765
  • I can't believe it was that simple. And I can't believe I didn't thought of it. Many thanks ;) – ereOn Aug 31 '10 at 09:27
  • if A type is not convertible to B type, what should be the behavior ? – bjskishore123 Aug 31 '10 at 09:49
  • depending on eaxtly what you are doing, and who owns the list, std::copy may be worth a look as well, possibly with an inserter iterator – jk. Aug 31 '10 at 09:49
  • 3
    @bjskishore123: It will simply fail to compile. Where, how and with what diagnostic message - depends on the implementation. – AnT stands with Russia Aug 31 '10 at 09:59
  • +1: Simplicity is elegance. Note that the range of iterators can be used also with `insert` (about the only thing note mentioned here). – Matthieu M. Aug 31 '10 at 14:12