Reputation: 1092
In C++ I have the following code. I'm trying to copy the data stored in a vector into a matrix (inside a vector). I've tried to do this:
Vector<float> vec;
// Let's imagine that vec contains 10 float values: {1,2,3 ...., 10}
// I'd like to copy those numbers into a Mat variable
Vector<Mat> myMats;
myMats.push_back(Mat(2,5,CV_32FC1,&vec.front()));
It works. However!, when modifying the content on the vector "vec" and trying to insert it in another position in my vector of Mat, all of them get the value of the last "push_back" operation. All entries in "myMats" are overwritten with the last entry. How can I solve this?
I think the problem is using the reference ("&") that modifies each time the address, where to look.
Upvotes: 2
Views: 1473
Reputation: 20294
The OP has already solved it by himself. However, this is some clarification if someone come to this question later.
cv::Mat
is a container with a pointer to the actual data. When you create a cv::Mat
like this:
cv::Mat some_mat;
The cv::Mat
is created in the stack and it will point to the data in the heap by keeping a pointer in its struct. When you copy a cv::Mat
using its copy constructor/Assignment like this:
cv::Mat another_mat=some_mat;
or this:
some_vector_of_mats.push_back(some_mat);
a shallow copy will happen. In other words, the header of the cv::Mat
(rows and columns count, type...) will be deeply copied and The pointer that points to the actual data will be shallow copied. But the actual data will not be copied. So what happened in the OP case that each time a cv::Mat is pushed to the vector a shallow copy is happend. The pointer copied with no change in its value. So, all the cv::Mat's are pointing to the same place. Thus leads to any change in one of them data will affect the others.
Upvotes: 1
Reputation: 1092
Ok. I've figured out how to do it (creating a temporary Mat)
Mat temp_;
temp_ = Mat(2,5,CV_32FC1,&vec.front());
myMats.push_back(temp_.clone());
I guess there is a more efficient way but this works ok.
Upvotes: 2