Commit d0e89337 authored by Vladislav Vinogradov's avatar Vladislav Vinogradov

refactored StereoBeliefPropagation

parent dd6d58f8
...@@ -65,61 +65,55 @@ public: ...@@ -65,61 +65,55 @@ public:
CV_EXPORTS Ptr<gpu::StereoBM> createStereoBM(int numDisparities = 64, int blockSize = 19); CV_EXPORTS Ptr<gpu::StereoBM> createStereoBM(int numDisparities = 64, int blockSize = 19);
/////////////////////////////////////////
// StereoBeliefPropagation
//! "Efficient Belief Propagation for Early Vision" P.Felzenszwalb
// "Efficient Belief Propagation for Early Vision" class CV_EXPORTS StereoBeliefPropagation : public cv::StereoMatcher
// P.Felzenszwalb
class CV_EXPORTS StereoBeliefPropagation
{ {
public: public:
enum { DEFAULT_NDISP = 64 }; using cv::StereoMatcher::compute;
enum { DEFAULT_ITERS = 5 };
enum { DEFAULT_LEVELS = 5 };
static void estimateRecommendedParams(int width, int height, int& ndisp, int& iters, int& levels); virtual void compute(InputArray left, InputArray right, OutputArray disparity, Stream& stream) = 0;
//! the default constructor //! version for user specified data term
explicit StereoBeliefPropagation(int ndisp = DEFAULT_NDISP, virtual void compute(InputArray data, OutputArray disparity, Stream& stream = Stream::Null()) = 0;
int iters = DEFAULT_ITERS,
int levels = DEFAULT_LEVELS,
int msg_type = CV_32F);
//! the full constructor taking the number of disparities, number of BP iterations on each level, //! number of BP iterations on each level
//! number of levels, truncation of data cost, data weight, virtual int getNumIters() const = 0;
//! truncation of discontinuity cost and discontinuity single jump virtual void setNumIters(int iters) = 0;
//! DataTerm = data_weight * min(fabs(I2-I1), max_data_term)
//! DiscTerm = min(disc_single_jump * fabs(f1-f2), max_disc_term)
//! please see paper for more details
StereoBeliefPropagation(int ndisp, int iters, int levels,
float max_data_term, float data_weight,
float max_disc_term, float disc_single_jump,
int msg_type = CV_32F);
//! the stereo correspondence operator. Finds the disparity for the specified rectified stereo pair, //! number of levels
//! if disparity is empty output type will be CV_16S else output type will be disparity.type(). virtual int getNumLevels() const = 0;
void operator()(const GpuMat& left, const GpuMat& right, GpuMat& disparity, Stream& stream = Stream::Null()); virtual void setNumLevels(int levels) = 0;
//! truncation of data cost
virtual double getMaxDataTerm() const = 0;
virtual void setMaxDataTerm(double max_data_term) = 0;
//! version for user specified data term //! data weight
void operator()(const GpuMat& data, GpuMat& disparity, Stream& stream = Stream::Null()); virtual double getDataWeight() const = 0;
virtual void setDataWeight(double data_weight) = 0;
int ndisp; //! truncation of discontinuity cost
virtual double getMaxDiscTerm() const = 0;
virtual void setMaxDiscTerm(double max_disc_term) = 0;
int iters; //! discontinuity single jump
int levels; virtual double getDiscSingleJump() const = 0;
virtual void setDiscSingleJump(double disc_single_jump) = 0;
float max_data_term; virtual int getMsgType() const = 0;
float data_weight; virtual void setMsgType(int msg_type) = 0;
float max_disc_term;
float disc_single_jump;
int msg_type; static void estimateRecommendedParams(int width, int height, int& ndisp, int& iters, int& levels);
private:
GpuMat u, d, l, r, u2, d2, l2, r2;
std::vector<GpuMat> datas;
GpuMat out;
}; };
CV_EXPORTS Ptr<gpu::StereoBeliefPropagation>
createStereoBeliefPropagation(int ndisp = 64, int iters = 5, int levels = 5, int msg_type = CV_32F);
// "A Constant-Space Belief Propagation Algorithm for Stereo Matching" // "A Constant-Space Belief Propagation Algorithm for Stereo Matching"
// Qingxiong Yang, Liang Wang, Narendra Ahuja // Qingxiong Yang, Liang Wang, Narendra Ahuja
// http://vision.ai.uiuc.edu/~qyang6/ // http://vision.ai.uiuc.edu/~qyang6/
......
...@@ -107,13 +107,13 @@ PERF_TEST_P(ImagePair, StereoBeliefPropagation, ...@@ -107,13 +107,13 @@ PERF_TEST_P(ImagePair, StereoBeliefPropagation,
if (PERF_RUN_GPU()) if (PERF_RUN_GPU())
{ {
cv::gpu::StereoBeliefPropagation d_bp(ndisp); cv::Ptr<cv::gpu::StereoBeliefPropagation> d_bp = cv::gpu::createStereoBeliefPropagation(ndisp);
const cv::gpu::GpuMat d_imgLeft(imgLeft); const cv::gpu::GpuMat d_imgLeft(imgLeft);
const cv::gpu::GpuMat d_imgRight(imgRight); const cv::gpu::GpuMat d_imgRight(imgRight);
cv::gpu::GpuMat dst; cv::gpu::GpuMat dst;
TEST_CYCLE() d_bp(d_imgLeft, d_imgRight, dst); TEST_CYCLE() d_bp->compute(d_imgLeft, d_imgRight, dst);
GPU_SANITY_CHECK(dst); GPU_SANITY_CHECK(dst);
} }
......
This diff is collapsed.
...@@ -106,10 +106,15 @@ GPU_TEST_P(StereoBeliefPropagation, Regression) ...@@ -106,10 +106,15 @@ GPU_TEST_P(StereoBeliefPropagation, Regression)
ASSERT_FALSE(right_image.empty()); ASSERT_FALSE(right_image.empty());
ASSERT_FALSE(disp_gold.empty()); ASSERT_FALSE(disp_gold.empty());
cv::gpu::StereoBeliefPropagation bp(64, 8, 2, 25, 0.1f, 15, 1, CV_16S); cv::Ptr<cv::gpu::StereoBeliefPropagation> bp = cv::gpu::createStereoBeliefPropagation(64, 8, 2, CV_16S);
bp->setMaxDataTerm(25.0);
bp->setDataWeight(0.1);
bp->setMaxDiscTerm(15.0);
bp->setDiscSingleJump(1.0);
cv::gpu::GpuMat disp; cv::gpu::GpuMat disp;
bp(loadMat(left_image), loadMat(right_image), disp); bp->compute(loadMat(left_image), loadMat(right_image), disp);
cv::Mat h_disp(disp); cv::Mat h_disp(disp);
h_disp.convertTo(h_disp, disp_gold.depth()); h_disp.convertTo(h_disp, disp_gold.depth());
......
...@@ -66,7 +66,7 @@ private: ...@@ -66,7 +66,7 @@ private:
gpu::GpuMat d_left, d_right; gpu::GpuMat d_left, d_right;
Ptr<gpu::StereoBM> bm; Ptr<gpu::StereoBM> bm;
gpu::StereoBeliefPropagation bp; Ptr<gpu::StereoBeliefPropagation> bp;
gpu::StereoConstantSpaceBP csbp; gpu::StereoConstantSpaceBP csbp;
int64 work_begin; int64 work_begin;
...@@ -173,7 +173,7 @@ void App::run() ...@@ -173,7 +173,7 @@ void App::run()
// Set common parameters // Set common parameters
bm = gpu::createStereoBM(p.ndisp); bm = gpu::createStereoBM(p.ndisp);
bp.ndisp = p.ndisp; bp = gpu::createStereoBeliefPropagation(p.ndisp);
csbp.ndisp = p.ndisp; csbp.ndisp = p.ndisp;
// Prepare disparity map of specified type // Prepare disparity map of specified type
...@@ -203,7 +203,7 @@ void App::run() ...@@ -203,7 +203,7 @@ void App::run()
} }
bm->compute(d_left, d_right, d_disp); bm->compute(d_left, d_right, d_disp);
break; break;
case Params::BP: bp(d_left, d_right, d_disp); break; case Params::BP: bp->compute(d_left, d_right, d_disp); break;
case Params::CSBP: csbp(d_left, d_right, d_disp); break; case Params::CSBP: csbp(d_left, d_right, d_disp); break;
} }
workEnd(); workEnd();
...@@ -232,8 +232,8 @@ void App::printParams() const ...@@ -232,8 +232,8 @@ void App::printParams() const
cout << "prefilter_sobel: " << bm->getPreFilterType() << endl; cout << "prefilter_sobel: " << bm->getPreFilterType() << endl;
break; break;
case Params::BP: case Params::BP:
cout << "iter_count: " << bp.iters << endl; cout << "iter_count: " << bp->getNumIters() << endl;
cout << "level_count: " << bp.levels << endl; cout << "level_count: " << bp->getNumLevels() << endl;
break; break;
case Params::CSBP: case Params::CSBP:
cout << "iter_count: " << csbp.iters << endl; cout << "iter_count: " << csbp.iters << endl;
...@@ -305,14 +305,14 @@ void App::handleKey(char key) ...@@ -305,14 +305,14 @@ void App::handleKey(char key)
p.ndisp = p.ndisp == 1 ? 8 : p.ndisp + 8; p.ndisp = p.ndisp == 1 ? 8 : p.ndisp + 8;
cout << "ndisp: " << p.ndisp << endl; cout << "ndisp: " << p.ndisp << endl;
bm->setNumDisparities(p.ndisp); bm->setNumDisparities(p.ndisp);
bp.ndisp = p.ndisp; bp->setNumDisparities(p.ndisp);
csbp.ndisp = p.ndisp; csbp.ndisp = p.ndisp;
break; break;
case 'q': case 'Q': case 'q': case 'Q':
p.ndisp = max(p.ndisp - 8, 1); p.ndisp = max(p.ndisp - 8, 1);
cout << "ndisp: " << p.ndisp << endl; cout << "ndisp: " << p.ndisp << endl;
bm->setNumDisparities(p.ndisp); bm->setNumDisparities(p.ndisp);
bp.ndisp = p.ndisp; bp->setNumDisparities(p.ndisp);
csbp.ndisp = p.ndisp; csbp.ndisp = p.ndisp;
break; break;
case '2': case '2':
...@@ -332,8 +332,8 @@ void App::handleKey(char key) ...@@ -332,8 +332,8 @@ void App::handleKey(char key)
case '3': case '3':
if (p.method == Params::BP) if (p.method == Params::BP)
{ {
bp.iters += 1; bp->setNumIters(bp->getNumIters() + 1);
cout << "iter_count: " << bp.iters << endl; cout << "iter_count: " << bp->getNumIters() << endl;
} }
else if (p.method == Params::CSBP) else if (p.method == Params::CSBP)
{ {
...@@ -344,8 +344,8 @@ void App::handleKey(char key) ...@@ -344,8 +344,8 @@ void App::handleKey(char key)
case 'e': case 'E': case 'e': case 'E':
if (p.method == Params::BP) if (p.method == Params::BP)
{ {
bp.iters = max(bp.iters - 1, 1); bp->setNumIters(max(bp->getNumIters() - 1, 1));
cout << "iter_count: " << bp.iters << endl; cout << "iter_count: " << bp->getNumIters() << endl;
} }
else if (p.method == Params::CSBP) else if (p.method == Params::CSBP)
{ {
...@@ -356,8 +356,8 @@ void App::handleKey(char key) ...@@ -356,8 +356,8 @@ void App::handleKey(char key)
case '4': case '4':
if (p.method == Params::BP) if (p.method == Params::BP)
{ {
bp.levels += 1; bp->setNumLevels(bp->getNumLevels() + 1);
cout << "level_count: " << bp.levels << endl; cout << "level_count: " << bp->getNumLevels() << endl;
} }
else if (p.method == Params::CSBP) else if (p.method == Params::CSBP)
{ {
...@@ -368,8 +368,8 @@ void App::handleKey(char key) ...@@ -368,8 +368,8 @@ void App::handleKey(char key)
case 'r': case 'R': case 'r': case 'R':
if (p.method == Params::BP) if (p.method == Params::BP)
{ {
bp.levels = max(bp.levels - 1, 1); bp->setNumLevels(max(bp->getNumLevels() - 1, 1));
cout << "level_count: " << bp.levels << endl; cout << "level_count: " << bp->getNumLevels() << endl;
} }
else if (p.method == Params::CSBP) else if (p.method == Params::CSBP)
{ {
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment