Vector of a class that inherits from a standard OpenCV class
Hi all,
I try to run this code but I have some troubles. The code is the following:
class point3D_t : public cv::Point3f { public: int label; int frame; double value; }; class point2D_t : public cv::Point2f { public: int label; int frame; double value; }; int main(int argc, const char * argv[]) { std::vector<point3D_t> input; std::vector<point2D_t> output; cv::Mat R,T,K; std::vector<double> distCoeffs; cv::projectPoints(input, R, T, K, distCoeffs, output); return 0; }
It gives me back as error in:
#include <opencv2/opencv.hpp> #include "opencv2/core.hpp" #include "opencv2/core/traits.hpp" template<typename _Tp> inline _InputArray::_InputArray(const std::vector<_Tp>& vec) { init(FIXED_TYPE + STD_VECTOR + traits::Type<_Tp>::value + ACCESS_READ, &vec); }
this:
Incomplete definition of type 'cv::traits::Type<point3D_t>'
@mshabunin suggest me:
You have to specify cv::traits::Type<...> in your code to be able to use custom types like this
But I do not know what doesn't means.
In the mean time I do that:
template <> class cv::DataType<cv::Point2f> { public: typedef point2D_t value_type; typedef point2D_t work_type; typedef float channel_type; enum { generic_type = 0, channels = 2, fmt = traits::SafeFmt<channel_type>::fmt + ((channels - 1) << 8) }; }; namespace cv::traits { template<> struct Depth<point2D_t> { enum { value = Depth<cv::Point2f>::value }; }; template<> struct Type<point2D_t> { enum { value = CV_MAKETYPE(Depth<point2D_t>::value, 2) }; }; }
and
template <> class cv::DataType<cv::Point3f> { public: typedef point3D_t value_type; typedef point3D_t work_type; typedef float channel_type; enum { generic_type = 0, channels = 3, fmt = traits::SafeFmt<channel_type>::fmt + ((channels - 1) << 8) }; }; namespace cv::traits { template<> struct Depth<point3D_t> { enum { value = Depth<cv::Point3f>::value }; }; template<> struct Type<point3D_t> { enum { value = CV_MAKETYPE(Depth<point3D_t>::value, 3) }; }; }
the error went away. However I have problem in run time. As if the memory was corrupted
can you explain, why you need this design ?
this is a simplification of my design. In reality my 2D and 3D class have a lot of stuff inside. However I would like that are compatible with the opencv function.
^ i asked: why ?
Ok sorry, In my code I have a lot of function that works on my class point3D_t and point2D_t. I store into that information like color label and other stuff. I also have heredity the base OpenCV points class to take advantage of all the function defined in that class. Moreover I would like to use the function defined in OpenCV like cv::projectPoints(). in my stupidity I thought that heredity a standard OpenCV class it is enough. If you think there is a more suitable design?
@berak what you think?
your classes are not binary compatible to the opencv ones they inherit from. and the Datatype templates do not respect your extra class members (label,frame,value). there will be internal "slicing", where they expect consecutive memory with either 2 or 3 elements, and that's where it'll crash.
again, inheritance works fine, when you have interfaces, virtual functions, references and that, NOT for primitive types, where exact memory layout is required
any chance you can achieve what you need without this terrible design (OOP overengineering) ?
Ok so there is a way to fix the Datatype templates to respect my extra class members? I understand that inherit a primitive types is not a good idea. Maybe I should have used another approach. But that is a way to fix this situation without rewrote all the code?