Jiadong
Jiadong

Reputation: 2072

Is there any fast way to convert std::vector<std::vector<float>> to std::vector<float2>?

I'd like to convert std::vector<std::vector<float>> into std::vector<float2>. The direct way is like this:

std::vector<std::vector<float>> pts;
std::vector<float> p1{1.,2.};
std::vector<float> p2{2.,3.};
pts.push_back(p1);
pts.push_back(p2);
std::vector<float2> lattice;
for (auto p : pts){
    p_ = make_float2(p[0],p[1]);
    lattice.push_back(p_);
}

Here float2 is cuda vector types, it is defined like this (not 100% sure):

struct __device_builtin__ __align__(8) float2
{
    float x, y ;
};

There is any other quick method?

Upvotes: 1

Views: 335

Answers (1)

Fantastic Mr Fox
Fantastic Mr Fox

Reputation: 33864

There are a couple of things you can do. 1 is use a type that means you know that there will always be 2 elements, such as:

std::vector<std::array<float, 2>>

or

std::vector<std::pair<float, float>>

This will mean you don't need to check that your internal vector is the right size before creating each point for safe code.

Secondly, reserve the right amount of space in your lattice vector before you begin emplacing back, this will mean that you will never have to resize and you won't waste time copying:

std::vector<float2> lattice;
lattice.reserve(pts.size());
for (auto p : pts){
    lattice.emplace_back(make_float2(p[0],p[1]));
}

Note, this requires that the float2 structure supports move (which it will based on the definition provided).

If you run a test on these two methods as done here. You will see that you can heavily reduce the time it will take. In the example that is linked, over 10000 points, the time is roughly 1/5th of the original time with my suggested changes.

Upvotes: 3

Related Questions