我正在编写一个大量使用OpenCV的C++应用程序。不幸的是,我想使用的一些OpenCV代码尚未被其API公开。特别是,我要使用的是一个级联检测.cpp(在下面引用)中的结构LBPEvaluator::Feature。我知道我不能简单地使用“#include Cascadedetect.cpp”,因为它会使链接器与多个已定义符号混淆。我认为有比将代码复制,粘贴和重命名到我的一个源文件中更好的解决方案了? 访问第三方API未公开的第三方C++函数和类的一般策略是什么?
提前谢谢了。
我尝试使用的特定代码:
class LBPEvaluator : public FeatureEvaluator
{
public:
struct Feature
{
Feature();
Feature( int x, int y, int _block_w, int _block_h ) :
rect(x, y, _block_w, _block_h) {}
int calc( int offset ) const;
void updatePtrs( const Mat& sum );
bool read(const FileNode& node );
Rect rect; // weight and height for block
const int* p[16]; // fast
};
LBPEvaluator();
virtual ~LBPEvaluator();
virtual bool read( const FileNode& node );
virtual Ptr<FeatureEvaluator> clone() const;
virtual int getFeatureType() const { return FeatureEvaluator::LBP; }
virtual bool setImage(const Mat& image, Size _origWinSize);
virtual bool setWindow(Point pt);
int operator()(int featureIdx) const
{ return featuresPtr[featureIdx].calc(offset); }
virtual int calcCat(int featureIdx) const
{ return (*this)(featureIdx); }
private:
Size origWinSize;
Ptr<vector<Feature> > features;
Feature* featuresPtr; // optimization
Mat sum0, sum;
Rect normrect;
int offset;
};
inline LBPEvaluator::Feature :: Feature()
{
rect = Rect();
for( int i = 0; i < 16; i++ )
p[i] = 0;
}
inline int LBPEvaluator::Feature :: calc( int offset ) const
{
int cval = CALC_SUM_( p[5], p[6], p[9], p[10], offset );
return (CALC_SUM_( p[0], p[1], p[4], p[5], offset ) >= cval ? 128 : 0) | // 0
(CALC_SUM_( p[1], p[2], p[5], p[6], offset ) >= cval ? 64 : 0) | // 1
(CALC_SUM_( p[2], p[3], p[6], p[7], offset ) >= cval ? 32 : 0) | // 2
(CALC_SUM_( p[6], p[7], p[10], p[11], offset ) >= cval ? 16 : 0) | // 5
(CALC_SUM_( p[10], p[11], p[14], p[15], offset ) >= cval ? 8 : 0)| // 8
(CALC_SUM_( p[9], p[10], p[13], p[14], offset ) >= cval ? 4 : 0)| // 7
(CALC_SUM_( p[8], p[9], p[12], p[13], offset ) >= cval ? 2 : 0)| // 6
(CALC_SUM_( p[4], p[5], p[8], p[9], offset ) >= cval ? 1 : 0);
}
inline void LBPEvaluator::Feature :: updatePtrs( const Mat& sum )
{
const int* ptr = (const int*)sum.data;
size_t step = sum.step/sizeof(ptr[0]);
Rect tr = rect;
CV_SUM_PTRS( p[0], p[1], p[4], p[5], ptr, tr, step );
tr.x += 2*rect.width;
CV_SUM_PTRS( p[2], p[3], p[6], p[7], ptr, tr, step );
tr.y += 2*rect.height;
CV_SUM_PTRS( p[10], p[11], p[14], p[15], ptr, tr, step );
tr.x -= 2*rect.width;
CV_SUM_PTRS( p[8], p[9], p[12], p[13], ptr, tr, step );
}
bool LBPEvaluator::Feature :: read(const FileNode& node )
{
FileNode rnode = node[CC_RECT];
FileNodeIterator it = rnode.begin();
it >> rect.x >> rect.y >> rect.width >> rect.height;
return true;
}
LBPEvaluator::LBPEvaluator()
{
features = new vector<Feature>();
}
LBPEvaluator::~LBPEvaluator()
{
}
bool LBPEvaluator::read( const FileNode& node )
{
features->resize(node.size());
featuresPtr = &(*features)[0];
FileNodeIterator it = node.begin(), it_end = node.end();
for(int i = 0; it != it_end; ++it, i++)
{
if(!featuresPtr[i].read(*it))
return false;
}
return true;
}
Ptr<FeatureEvaluator> LBPEvaluator::clone() const
{
LBPEvaluator* ret = new LBPEvaluator;
ret->origWinSize = origWinSize;
ret->features = features;
ret->featuresPtr = &(*ret->features)[0];
ret->sum0 = sum0, ret->sum = sum;
ret->normrect = normrect;
ret->offset = offset;
return ret;
}
bool LBPEvaluator::setImage( const Mat& image, Size _origWinSize )
{
int rn = image.rows+1, cn = image.cols+1;
origWinSize = _origWinSize;
if( image.cols < origWinSize.width || image.rows < origWinSize.height )
return false;
if( sum0.rows < rn || sum0.cols < cn )
sum0.create(rn, cn, CV_32S);
sum = Mat(rn, cn, CV_32S, sum0.data);
integral(image, sum);
size_t fi, nfeatures = features->size();
for( fi = 0; fi < nfeatures; fi++ )
featuresPtr[fi].updatePtrs( sum );
return true;
}
bool LBPEvaluator::setWindow( Point pt )
{
if( pt.x < 0 || pt.y < 0 ||
pt.x + origWinSize.width >= sum.cols-2 ||
pt.y + origWinSize.height >= sum.rows-2 )
return false;
offset = pt.y * ((int)sum.step/sizeof(int)) + pt.x;
return true;
}
Ptr<FeatureEvaluator> FeatureEvaluator::create(int featureType)
{
return featureType == HAAR ? Ptr<FeatureEvaluator>(new HaarEvaluator) :
featureType == LBP ? Ptr<FeatureEvaluator>(new LBPEvaluator) : Ptr<FeatureEvaluator>();
}
最佳答案
我的一般策略是而不是访问未通过其公共(public)接口(interface)公开的第三方功能和/或类。
它们不是公共(public)的事实意味着它们可以在发行版和下一个发行版之间进行更改,因此您不应对其进行依赖。
编辑
如果它是开放源代码(和/或您有权复制它)并且确实需要此功能,则可以提取相关部分并亲自进行维护。这使您免受原始代码可能更改的事实的影响。您将重复相同的代码,这违反了DRY principle,但是我猜这是可以容忍的。
关于c++ - 公开第三方C++函数和类,我们在Stack Overflow上找到一个类似的问题:https://stackoverflow.com/questions/4934324/