Added threshold_filter_singular_values()

This commit is contained in:
Davis King 2013-12-08 10:46:51 -05:00
parent 30963435cc
commit 03a34a69d1
2 changed files with 91 additions and 0 deletions

View File

@ -916,6 +916,70 @@ namespace dlib
return fb.num_separable_filters();
}
// ----------------------------------------------------------------------------------------
template <
typename Pyramid_type
>
object_detector<scan_fhog_pyramid<Pyramid_type> > threshold_filter_singular_values (
const object_detector<scan_fhog_pyramid<Pyramid_type> >& detector,
double thresh,
const unsigned long weight_index = 0
)
{
// make sure requires clause is not broken
DLIB_ASSERT(thresh > 0 ,
"\t object_detector threshold_filter_singular_values()"
<< "\n\t Invalid inputs were given to this function."
<< "\n\t thresh: " << thresh
);
DLIB_ASSERT(weight_index < detector.num_detectors(),
"\t object_detector threshold_filter_singular_values()"
<< "\n\t Invalid arguments were given to this function. "
<< "\n\t weight_index: " << weight_index
<< "\n\t detector.num_detectors(): " << detector.num_detectors()
);
DLIB_ASSERT(detector.get_w(weight_index).size() >= detector.get_scanner().get_num_dimensions() ,
"\t object_detector threshold_filter_singular_values()"
<< "\n\t Invalid arguments were given to this function. "
<< "\n\t detector.get_w(weight_index).size(): " << detector.get_w(weight_index).size()
<< "\n\t detector.get_scanner().get_num_dimensions(): " << detector.get_scanner().get_num_dimensions()
);
const unsigned long width = detector.get_scanner().get_fhog_window_width();
const unsigned long height = detector.get_scanner().get_fhog_window_height();
const long size = width*height;
std::vector<matrix<double,0,1> > detector_weights;
for (unsigned long j = 0; j < detector.num_detectors(); ++j)
{
matrix<double,0,1> weights = detector.get_w(j);
if (j == weight_index)
{
matrix<double> u,v,w,f;
for (int i = 0; i < 31; ++i)
{
f = reshape(rowm(weights, range(i*size, (i+1)*size-1)), height, width);
svd3(f, u,w,v);
const double scaled_thresh = std::max(1e-3, max(w)*thresh);
w = round_zeros(w, scaled_thresh);
f = u*diagm(w)*trans(v);
set_rowm(weights,range(i*size, (i+1)*size-1)) = reshape_to_column_vector(f);
}
}
detector_weights.push_back(weights);
}
return object_detector<scan_fhog_pyramid<Pyramid_type> >(detector.get_scanner(),
detector.get_overlap_tester(),
detector_weights);
}
// ----------------------------------------------------------------------------------------
template <

View File

@ -54,6 +54,33 @@ namespace dlib
defined by detector.get_w(weight_index).
!*/
// ----------------------------------------------------------------------------------------
template <
typename Pyramid_type
>
object_detector<scan_fhog_pyramid<Pyramid_type> > threshold_filter_singular_values (
const object_detector<scan_fhog_pyramid<Pyramid_type> >& detector,
double thresh,
const unsigned long weight_index = 0
);
/*!
requires
- thresh > 0
- weight_index < detector.num_detectors()
- detector.get_w(weight_index).size() >= detector.get_scanner().get_num_dimensions()
(i.e. the detector must have been populated with a HOG filter)
ensures
- Removes all components of the filters in the given detector that have
singular values that are smaller than the given threshold. Therefore, this
function allows you to control how many separable filters are in a detector.
In particular, as thresh gets larger the quantity
num_separable_filters(threshold_filter_singular_values(detector,thresh,weight_index),weight_index)
will generally get smaller and therefore give a faster running detector.
However, note that at some point a large enough thresh will drop too much
information from the filters and their accuracy will suffer.
!*/
// ----------------------------------------------------------------------------------------
template <