@ -58,34 +58,39 @@ using std::string;
using std : : min ;
using std : : max ;
namespace cv
{
namespace xobjdetect
{
void ICFDetector : : train ( const String & pos_path ,
const String & bg_path ,
void ICFDetector : : train ( const vector < String > & pos_filenames ,
const vector < String > & bg_filenames ,
ICFDetectorParams params )
{
vector < String > pos_filenames ;
glob ( pos_path , pos_filenames ) ;
vector < String > bg_filenames ;
glob ( bg_path , bg_filenames ) ;
int color ;
if ( params . is_grayscale = = false )
color = IMREAD_COLOR ;
else
color = IMREAD_GRAYSCALE ;
model_n_rows_ = params . model_n_rows ;
model_n_cols_ = params . model_n_cols ;
ftype_ = params . features_type ;
Size model_size ( params . model_n_cols , params . model_n_rows ) ;
vector < Mat > samples ; /* positive samples + negative samples */
Mat sample , resized_sample ;
int pos_count = 0 ;
for ( size_t i = 0 ; i < pos_filenames . size ( ) ; + + i , + + pos_count )
{
cout < < setw ( 6 ) < < ( i + 1 ) < < " / " < < pos_filenames . size ( ) < < " \r " ;
Mat img = imread ( pos_filenames [ i ] ) ;
Mat img = imread ( pos_filenames [ i ] , color ) ;
resize ( img , resized_sample , model_size ) ;
samples . push_back ( resized_sample . clone ( ) ) ;
}
@ -96,18 +101,16 @@ void ICFDetector::train(const String& pos_path,
for ( size_t i = 0 ; i < bg_filenames . size ( ) ; + + i )
{
cout < < setw ( 6 ) < < ( i + 1 ) < < " / " < < bg_filenames . size ( ) < < " \r " ;
Mat img = imread ( bg_filenames [ i ] ) ;
Mat img = imread ( bg_filenames [ i ] , color ) ;
for ( int j = 0 ; j < params . bg_per_image ; + + j , + + neg_count )
{
Rect r ;
r . x = rng . uniform ( 0 , img . cols ) ;
r . width = rng . uniform ( r . x + 1 , img . cols ) ;
r . y = rng . uniform ( 0 , img . rows ) ;
r . height = rng . uniform ( r . y + 1 , img . rows ) ;
sample = img . colRange ( r . x , r . width ) . rowRange ( r . y , r . height ) ;
resize ( sample , resized_sample , model_size ) ;
samples . push_back ( resized_sample . clone ( ) ) ;
r . x = rng . uniform ( 0 , img . cols - model_size . width ) ;
r . width = model_size . width ;
r . y = rng . uniform ( 0 , img . rows - model_size . height ) ;
r . height = model_size . height ;
sample = img . colRange ( r . x , r . x + r . width ) . rowRange ( r . y , r . y + r . height ) ;
samples . push_back ( sample . clone ( ) ) ;
}
}
cout < < " \n " ;
@ -118,9 +121,15 @@ void ICFDetector::train(const String& pos_path,
for ( int i = pos_count ; i < pos_count + neg_count ; + + i )
labels ( 0 , i ) = - 1 ;
vector < vector < int > > features = generateFeatures ( model_size , " icf " ,
params . feature_count ) ;
Ptr < FeatureEvaluator > evaluator = createFeatureEvaluator ( features , " icf " ) ;
vector < vector < int > > features ;
if ( params . is_grayscale = = false )
features = generateFeatures ( model_size , params . features_type , params . feature_count , 10 ) ;
else
features = generateFeatures ( model_size , params . features_type , params . feature_count , 7 ) ;
Ptr < FeatureEvaluator > evaluator = createFeatureEvaluator ( features , params . features_type ) ;
Mat_ < int > data = Mat_ < int > : : zeros ( ( int ) features . size ( ) , ( int ) samples . size ( ) ) ;
Mat_ < int > feature_col ( 1 , ( int ) samples . size ( ) ) ;
@ -141,13 +150,13 @@ void ICFDetector::train(const String& pos_path,
}
cout < < " \n " ;
samples . clear ( ) ;
WaldBoostParams wparams ;
wparams . weak_count = params . weak_count ;
wparams . alpha = 0.02f ;
wparams . alpha = params . alpha ;
waldboost_ = createWaldBoost ( wparams ) ;
vector < int > indices = waldboost_ - > train ( data , labels ) ;
vector < int > indices = waldboost_ - > train ( data , labels , params . use_fast_log ) ;
cout < < " indices: " ;
for ( size_t i = 0 ; i < indices . size ( ) ; + + i )
cout < < indices [ i ] < < " " ;
@ -163,6 +172,7 @@ void ICFDetector::write(FileStorage& fs) const
fs < < " { " ;
fs < < " model_n_rows " < < model_n_rows_ ;
fs < < " model_n_cols " < < model_n_cols_ ;
fs < < " ftype " < < String ( ftype_ . c_str ( ) ) ;
fs < < " waldboost " ;
waldboost_ - > write ( fs ) ;
fs < < " features " < < " [ " ;
@ -177,8 +187,11 @@ void ICFDetector::write(FileStorage& fs) const
void ICFDetector : : read ( const FileNode & node )
{
waldboost_ = Ptr < WaldBoost > ( createWaldBoost ( WaldBoostParams ( ) ) ) ;
String f_temp ;
node [ " model_n_rows " ] > > model_n_rows_ ;
node [ " model_n_cols " ] > > model_n_cols_ ;
f_temp = ( String ) node [ " ftype " ] ;
this - > ftype_ = ( string ) f_temp . c_str ( ) ;
waldboost_ - > read ( node [ " waldboost " ] ) ;
FileNode features = node [ " features " ] ;
features_ . clear ( ) ;
@ -191,49 +204,99 @@ void ICFDetector::read(const FileNode& node)
}
void ICFDetector : : detect ( const Mat & img , vector < Rect > & objects ,
float scaleFactor , Size minSize , Size maxSize , float threshold )
float scaleFactor , Size minSize , Size maxSize , float threshold , int slidingStep , std : : vector < float > & values )
{
float scale_from = min ( model_n_cols_ / ( float ) maxSize . width ,
model_n_rows_ / ( float ) maxSize . height ) ;
float scale_to = max ( model_n_cols_ / ( float ) minSize . width ,
model_n_rows_ / ( float ) minSize . height ) ;
objects . clear ( ) ;
Ptr < FeatureEvaluator > evaluator = createFeatureEvaluator ( features_ , " icf " ) ;
Ptr < FeatureEvaluator > evaluator = createFeatureEvaluator ( features_ , ftype_ ) ;
Mat rescaled_image ;
int step = 8 ;
vector < Mat > channels ;
for ( float scale = scale_from ; scale < scale_to + 0.001 ; scale * = scaleFactor )
{
cout < < " scale " < < scale < < endl ;
int new_width = int ( img . cols * scale ) ;
new_width - = new_width % 4 ;
int new_height = int ( img . rows * scale ) ;
new_height - = new_height % 4 ;
resize ( img , rescaled_image , Size ( new_width , new_height ) ) ;
computeChannels ( rescaled_image , channels ) ;
evaluator - > setChannels ( channels ) ;
for ( int row = 0 ; row < = rescaled_image . rows - model_n_rows_ ; row + = step )
for ( int row = 0 ; row < = rescaled_image . rows - model_n_rows_ ; row + = slidingStep )
{
for ( int col = 0 ; col < = rescaled_image . cols - model_n_cols_ ;
col + = slidingStep )
{
evaluator - > setPosition ( Size ( row , col ) ) ;
float value = waldboost_ - > predict ( evaluator ) ;
if ( value > threshold )
{
values . push_back ( value ) ;
int x = ( int ) ( col / scale ) ;
int y = ( int ) ( row / scale ) ;
int width = ( int ) ( model_n_cols_ / scale ) ;
int height = ( int ) ( model_n_rows_ / scale ) ;
objects . push_back ( Rect ( x , y , width , height ) ) ;
}
}
}
}
}
void ICFDetector : : detect ( const Mat & img , vector < Rect > & objects ,
float minScaleFactor , float maxScaleFactor , float factorStep , float threshold , int slidingStep , std : : vector < float > & values )
{
if ( factorStep < = 0 )
{
CV_Error ( CV_StsBadArg , " factorStep must be > 0 " ) ;
CV_Assert ( false ) ;
}
objects . clear ( ) ;
Ptr < FeatureEvaluator > evaluator = createFeatureEvaluator ( features_ , ftype_ ) ;
Mat rescaled_image ;
vector < Mat > channels ;
for ( float scale = minScaleFactor ; scale < maxScaleFactor + 0.001 ; scale + = factorStep )
{
if ( scale < 1.0 )
resize ( img , rescaled_image , Size ( ) , scale , scale , INTER_AREA ) ;
else if ( scale > 1.0 )
resize ( img , rescaled_image , Size ( ) , scale , scale , INTER_CUBIC ) ;
else //scale == 1.0
img . copyTo ( rescaled_image ) ;
computeChannels ( rescaled_image , channels ) ;
evaluator - > setChannels ( channels ) ;
for ( int row = 0 ; row < = rescaled_image . rows - model_n_rows_ ; row + = slidingStep )
{
for ( int col = 0 ; col < = rescaled_image . cols - model_n_cols_ ;
col + = step )
col + = slidingS tep )
{
evaluator - > setPosition ( Size ( row , col ) ) ;
float value = waldboost_ - > predict ( evaluator ) ;
if ( value > threshold )
{
values . push_back ( value ) ;
int x = ( int ) ( col / scale ) ;
int y = ( int ) ( row / scale ) ;
int width = ( int ) ( model_n_cols_ / scale ) ;
int height = ( int ) ( model_n_rows_ / scale ) ;
cout < < value < < " " < < x < < " " < < y < < " " < < width < < " "
< < height < < endl ;
objects . push_back ( Rect ( x , y , width , height ) ) ;
}
}
}
}
}
void write ( FileStorage & fs , String & , const ICFDetector & detector )