Screenplay: std::vector
And std::copy()
¶
std::vector<>
Into C Array¶
#include <vector>
#include <iostream>
int main()
{
std::vector<int> src = {100, 200, 300};
int dst[3];
std::copy(src.begin(), src.end(), dst);
for (int i: dst)
std::cout << i << std::endl;
return 0;
}
The code above allocates a C array on the stack, of sufficient size
⟶ this is crucial!
Copying Into std::vector
(Without Allocation)¶
Remember,
std::vector<>
is empty by defaultThis code will crash:
#include <vector>
#include <iostream>
#pragma GCC diagnostic push
#pragma GCC diagnostic ignored "-Wnonnull"
int main()
{
std::vector<int> src = {100, 200, 300};
std::vector<int> dst; // <--- ATTENTION: empty!!
std::copy(src.begin(), src.end(), dst.begin()); // <--- CRASH!
for (int i: dst)
std::cout << i << std::endl;
return 0;
}
#pragma GCC diagnostic pop
Solution 1: Pre-allocate Destination¶
Using
src.size()
Pre-initialization, allocating the destination just as big as needed
#include <vector>
#include <iostream>
int main()
{
std::vector<int> src = {100, 200, 300};
std::vector<int> dst(src.size()); // <-- initialize dst to contain three default-constructed elements
std::copy(src.begin(), src.end(), dst.begin()); // <--- those are overwritten here
for (int i: dst)
std::cout << i << std::endl;
return 0;
}
Using
.reserve()
if destination’s memory is not known to be pre-allocated
#include <vector>
#include <iostream>
int main()
{
std::vector<int> src = {100, 200, 300};
std::vector<int> dst;
dst.reserve(src.size()); // <--- makes dst contain three default-constructed element
std::copy(src.begin(), src.end(), dst.begin()); // <--- those are overwritten here
for (int i: dst)
std::cout << i << std::endl;
return 0;
}
Solution 2: std::back_insert_iterator
¶
Acts as if copied elements were appended with
.push_back()
#include <vector>
#include <iostream>
int main()
{
std::vector<int> src = {100, 200, 300};
std::vector<int> dst; // <-- empty
std::copy(src.begin(), src.end(),
std::back_insert_iterator<std::vector<int>>(dst));
for (int i: dst)
std::cout << i << std::endl;
return 0;
}