Daniel
Daniel

Reputation: 2592

Assign vector from pair<first,last>

I'd like to construct a vector from data provided by a 3rd party lib.

The lib holds the data and provides access to it like this:

const uint8_t* data;
std::pair<const uint8_t*, const uint8_t*> getvalue() const {
  return std::make_pair(data + offset, data + length);
}

For further processing this data I'd put it into a vector, but I'd like to avoid multiple calling of getvalue and if possible I'd also avoid creating a variable.

This is how I'm doing it now:

std::pair<const uint8_t*, const uint8_t*> dataPtrs = 3rdpartydata.getvalue();
vector<uint8_t> data(dataPtrs.first, dataPtrs.second);

It is working, but is there any way to make it better/simpler?

Upvotes: 2

Views: 177

Answers (1)

dfrib
dfrib

Reputation: 73176

Structured bindings

As of C++17, you can use structured bindings to bind the first and second members of std::pair<...> return value from getvalue():

const auto [data_begin, data_end] = thirdpartydata.getvalue();
const std::vector<uint8_t> v(data_begin, data_end);

C++17 also introduced class template argument deduction, meaning that you may omit the template argument in the declaration of v above, as it can be deduced:

const auto [data_begin, data_end] = thirdpartydata.getvalue();
const std::vector v(data_begin, data_end);

std::apply and a generic lambda

Alternatively, you could make use of another C++17 feature, std::apply, along with a generic lambda (C++14):

const auto v = std::apply([](auto a, auto b) { return std::vector(a, b); }, 
                          thirdpartydata.getvalue());

Note the use of class template argument deduction in the return statement of the lambda.

Upvotes: 2

Related Questions