Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Initialising a vector of std::string with an array

Tags:

c++

stl

I wish to initialise a vector using an array of std::strings.

I have the following solution, but wondered if there's a more elegant way of doing this?

std::string str[] = { "one", "two", "three", "four" };
vector< std::string > vec;
vec = vector< std::string >( str, str + ( sizeof ( str ) /  sizeof ( std::string ) ) );

I could, of course, make this more readable by defining the size as follows:

int size =  ( sizeof ( str ) /  sizeof ( std::string ) );

and replacing the vector initialisation with:

vec = vector< std::string >( str, str + size );

But this still feels a little "inelegant".

like image 699
Kris Dunning Avatar asked Jan 26 '12 14:01

Kris Dunning


2 Answers

Well the intermediate step isn't needed:

std::string str[] = { "one", "two", "three", "four" };
vector< std::string > vec( str, str + ( sizeof ( str ) /  sizeof ( std::string ) ) );

In C++11 you'd be able to put the brace initialization in the constructor using the initializer list constructor.

like image 124
Mark B Avatar answered Oct 02 '22 01:10

Mark B


In C++11, we have std::begin and std::end, which work for both STL-style containers and built-in arrays:

#include <iterator>

std::vector<std::string> vec(std::begin(str), std::end(str));

although, as mentioned in the comments, you usually won't need the intermediate array at all:

std::vector<std::string> vec {"one", "two", "three", "four"};

In C++03, you could use a template to deduce the size of the array, either to implement your own begin and end, or to initialise the array directly:

template <typename T, size_t N>
std::vector<T> make_vector(T &(array)[N]) {
    return std::vector<T>(array, array+N);
}

std::vector<std::string> vec = make_vector(str);
like image 31
Mike Seymour Avatar answered Oct 02 '22 00:10

Mike Seymour