add support for precomputed integrals
authormarina.kolpakova <marina.kolpakova@itseez.com>
Mon, 15 Oct 2012 17:55:57 +0000 (21:55 +0400)
committermarina.kolpakova <marina.kolpakova@itseez.com>
Sat, 10 Nov 2012 01:11:48 +0000 (05:11 +0400)
modules/gpu/perf/perf_softcascade.cpp
modules/gpu/src/softcascade.cpp
modules/gpu/test/test_softcascade.cpp

index d379d7f..582561c 100644 (file)
@@ -9,7 +9,7 @@
         virtual void __gpu();\
       virtual void PerfTestBody();\
     };\
-    TEST_P(fixture##_##name, name /*perf*/){ RunPerfTestBody(); if (runOnGpu) __gpu(); else __cpu();}\
+    TEST_P(fixture##_##name, name /*perf*/){ RunPerfTestBody(); if (PERF_RUN_GPU()) __gpu(); else __cpu();}\
     INSTANTIATE_TEST_CASE_P(/*none*/, fixture##_##name, params);\
     void fixture##_##name::PerfTestBody()
 
@@ -19,7 +19,7 @@
 #define RUN_GPU(fixture, name)\
     void fixture##_##name::__gpu()
 
-#define FAIL_NO_CPU(fixture, name)\
+#define NO_CPU(fixture, name)\
 void fixture##_##name::__cpu() { FAIL() << "No such CPU implementation analogy";}
 
 namespace {
@@ -184,7 +184,7 @@ RUN_GPU(SoftCascadeTestRoi, detectInRoi)
     SANITY_CHECK(sortDetections(curr));
 }
 
-FAIL_NO_CPU(SoftCascadeTestRoi, detectInRoi)
+NO_CPU(SoftCascadeTestRoi, detectInRoi)
 
 
 GPU_PERF_TEST_P(SoftCascadeTestRoi, detectEachRoi,
@@ -226,4 +226,52 @@ RUN_GPU(SoftCascadeTestRoi, detectEachRoi)
     SANITY_CHECK(sortDetections(curr));
 }
 
-FAIL_NO_CPU(SoftCascadeTestRoi, detectEachRoi)
+NO_CPU(SoftCascadeTestRoi, detectEachRoi)
+
+GPU_PERF_TEST_P(SoftCascadeTest, detectOnIntegral,
+    testing::Combine(
+        testing::Values(std::string("cv/cascadeandhog/sc_cvpr_2012_to_opencv.xml")),
+        testing::Values(std::string("cv/cascadeandhog/integrals.xml"))))
+{ }
+
+    static std::string itoa(long i)
+    {
+        static char s[65];
+        sprintf(s, "%ld", i);
+        return std::string(s);
+    }
+
+RUN_GPU(SoftCascadeTest, detectOnIntegral)
+{
+    cv::FileStorage fs(perf::TestBase::getDataPath(GET_PARAM(1)), cv::FileStorage::READ);
+    ASSERT_TRUE(fs.isOpened());
+
+    cv::gpu::GpuMat hogluv(121 * 10, 161, CV_32SC1);
+    for (int i = 0; i < 10; ++i)
+    {
+        cv::Mat channel;
+        fs[std::string("channel") + itoa(i)] >> channel;
+        cv::gpu::GpuMat gchannel(hogluv, cv::Rect(0, 121 * i, 161, 121));
+        gchannel.upload(channel);
+    }
+
+    cv::gpu::SoftCascade cascade;
+    ASSERT_TRUE(cascade.load(perf::TestBase::getDataPath(GET_PARAM(0))));
+
+    cv::gpu::GpuMat objectBoxes(1, 10000 * sizeof(cv::gpu::SoftCascade::Detection), CV_8UC1), rois(cascade.getRoiSize(), CV_8UC1), trois;
+    rois.setTo(1);
+    cv::gpu::transpose(rois, trois);
+
+    cv::gpu::GpuMat curr = objectBoxes;
+    cascade.detectMultiScale(hogluv, trois, curr);
+
+    TEST_CYCLE()
+    {
+        curr = objectBoxes;
+        cascade.detectMultiScale(hogluv, trois, curr);
+    }
+
+    SANITY_CHECK(sortDetections(curr));
+}
+
+NO_CPU(SoftCascadeTest, detectOnIntegral)
\ No newline at end of file
index 560c251..d9519e8 100644 (file)
@@ -526,17 +526,24 @@ void cv::gpu::SoftCascade::detectMultiScale(const GpuMat& colored, const GpuMat&
                                 GpuMat& objects, const int /*rejectfactor*/, int specificScale) const
 {
     // only color images are supperted
-    CV_Assert(colored.type() == CV_8UC3);
+    CV_Assert(colored.type() == CV_8UC3 || colored.type() == CV_32SC1);
 
     // we guess user knows about shrincage
     CV_Assert((rois.size().width == getRoiSize().height) && (rois.type() == CV_8UC1));
 
-    // only this window size allowed
-    CV_Assert(colored.cols == Filds::FRAME_WIDTH && colored.rows == Filds::FRAME_HEIGHT);
 
     Filds& flds = *filds;
 
-    flds.preprocess(colored);
+    if (colored.type() == CV_8UC3)
+    {
+        // only this window size allowed
+        CV_Assert(colored.cols == Filds::FRAME_WIDTH && colored.rows == Filds::FRAME_HEIGHT);
+        flds.preprocess(colored);
+    }
+    else
+    {
+        colored.copyTo(flds.hogluv);
+    }
 
     flds.detect(specificScale, rois, objects, 0);
 
index 04c3855..bf88029 100644 (file)
@@ -262,4 +262,37 @@ TEST(SoftCascadeTest, detect)
     cv::Mat detections(objectBoxes);
     ASSERT_EQ(detections.cols / sizeof(Detection) ,3670U);
 }
+
+TEST(SoftCascadeTest, detectOnIntegral)
+{
+    std::string xml =  cvtest::TS::ptr()->get_data_path() + "../cv/cascadeandhog/sc_cvpr_2012_to_opencv.xml";
+    cv::gpu::SoftCascade cascade;
+    ASSERT_TRUE(cascade.load(xml));
+
+    std::string intPath = cvtest::TS::ptr()->get_data_path() + "../cv/cascadeandhog/integrals.xml";
+    cv::FileStorage fs(intPath, cv::FileStorage::READ);
+    ASSERT_TRUE(fs.isOpened());
+
+    GpuMat hogluv(121 * 10, 161, CV_32SC1);
+    for (int i = 0; i < 10; ++i)
+    {
+        cv::Mat channel;
+        fs[std::string("channel") + SoftCascadeTest::itoa(i)] >> channel;
+        GpuMat gchannel(hogluv, cv::Rect(0, 121 * i, 161, 121));
+        gchannel.upload(channel);
+    }
+
+    GpuMat objectBoxes(1, 100000, CV_8UC1), rois(cascade.getRoiSize(), CV_8UC1);
+    rois.setTo(1);
+
+    cv::gpu::GpuMat trois;
+    cv::gpu::transpose(rois, trois);
+
+    cascade.detectMultiScale(hogluv, trois, objectBoxes);
+
+    typedef cv::gpu::SoftCascade::Detection Detection;
+    cv::Mat detections(objectBoxes);
+
+    ASSERT_EQ(detections.cols / sizeof(Detection) ,2042U);
+}
 #endif
\ No newline at end of file