⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 boosting.cpp

📁 这是一个实现Adaboost算法的程序
💻 CPP
📖 第 1 页 / 共 2 页
字号:
// Boosting.cpp: implementation of the Boosting class.
//
//////////////////////////////////////////////////////////////////////
#include "stdafx.h"
#include "BoostingLbp.h"
#include "Boosting.h"
#include "math.h"
#include "stdio.h"
#include "Define.h"
#include "HarrFeature.h"
#ifdef _DEBUG
#undef THIS_FILE
static char THIS_FILE[]=__FILE__;
#define new DEBUG_NEW
#endif

//////////////////////////////////////////////////////////////////////
// Construction/Destruction
//////////////////////////////////////////////////////////////////////
Boosting::Boosting(DWORD posNum, DWORD negNum)
{
        PositiveNum = posNum;
        NegativeNum = negNum;
        TotalNegativeNum = negNum;
        TotalSampleNum = PositiveNum + NegativeNum;

        unsigned char *pFlag = new unsigned char[TOTAL_FEATURE_NUM];
        //	FILE *fFlag = fopen(SAVEPATH + "flag", "rb");
        //	fread(pFlag, sizeof(unsigned char), TOTAL_FEATURE_NUM, fFlag);
        //	fclose(fFlag);
        memset(pFlag, 1, TOTAL_FEATURE_NUM);

        usedFeaCount = 0;
        for (int c=0; c<TOTAL_FEATURE_NUM; c++)
        {
                if (pFlag[c] == 1) usedFeaCount++;
        }
        delete []pFlag;

        BinMin = NULL;
        BinWidth = NULL;
        FeaValue = NULL;
        subWinInfo = new FeatureInfo[usedFeaCount];

        Weight = new double[TotalSampleNum];

        VotedValue = new double[TotalSampleNum];

        Label = new unsigned char[TotalSampleNum];

        memset(Label, 1 , PositiveNum);
        memset(Label + PositiveNum, 0, NegativeNum);
}

Boosting::~Boosting()
{
        delete []BinMin;
        BinMin = NULL;
        delete []BinWidth;
        BinWidth = NULL;

        delete []Weight;
        Weight = NULL;

        delete []VotedValue;
        VotedValue = NULL;

        delete []Label;
        Label = NULL;

        if (NULL != FeaValue)
        {
                for(int i=0; i<usedFeaCount; i++)
                {		
                        if(FeaValue[i] != NULL) 
                        {
                                delete [] FeaValue[i];
                                FeaValue[i] = NULL;
                        }
                }
                FeaValue = NULL;
        }

        if (subWinInfo != NULL) delete []subWinInfo;

        return;
}

//Quantize and the LBP bin distance.
void Boosting::Init(CString szPosName, CString szNegName)
{
        GetAllSubWinInfo();

        printf("\n");
        printf("Total Weak Learner: %d\n", usedFeaCount);
        printf("Positive Sample Number: %d\n", PositiveNum);
        printf("Negative Sample Number: %d\n", NegativeNum);
        printf("\n");

        CString szPosPath = szPosName;
        CString szNegPath = szNegName;

        FILE *PosFile = fopen(szPosPath, "rb");
        FILE *NegFile = fopen(szNegPath, "rb");

        //Quantize the distance to be between 0 and 99.
        BinMin   = new double[usedFeaCount];
        BinWidth = new double[usedFeaCount];

        FeaValue = new WORD*[usedFeaCount];

        for (int i=0; i<usedFeaCount; i++)
        {
                FeaValue[i] = new WORD[TotalSampleNum];
        }

        float *RawValue = new float[TotalSampleNum];

        for (i=0; i<usedFeaCount; i++)
        {
                //read in intra-distance.		
                fread(RawValue, sizeof(float), PositiveNum, PosFile);
                //read in extra-distance.
                fread(RawValue + PositiveNum, sizeof(float), NegativeNum, NegFile);

                Discretization(RawValue, i);
                printf("feaid = %d\r", i);
        }

        delete []RawValue;
        RawValue = NULL;

        fclose(PosFile);
        fclose(NegFile);

}

////////////////////////////////////////////////////////////////////
void Boosting::Discretization(float * RawValue, int FeatureNo)
{
        double MinFeaValue = 999999;
        double MaxFeaValue = -999999;

        for (int j=0; j<TotalSampleNum; j++)
        {
                if (RawValue[j] < MinFeaValue)
                {
                        MinFeaValue = RawValue[j];
                }
                if (RawValue[j] > MaxFeaValue)
                {
                        MaxFeaValue = RawValue[j];
                }
        }				

        BinWidth[FeatureNo] = (MaxFeaValue - MinFeaValue) / double(BINNUM);
        BinMin[FeatureNo]   = MinFeaValue;

        for (j=0; j<TotalSampleNum; j++)		
        {
                FeaValue [FeatureNo][j] = (RawValue[j] - BinMin[FeatureNo])
                        / double(BinWidth[FeatureNo]);
        }
}

////////////////////////////////////////////////////////////////////////
//Find the best weak classifier.
void Boosting::UpdateHistClassify(double* MinCriterion, int *SelectedFeaNo, 
                                  int *MinThreshold, int *MinSign)
{
        int    i, j;
        const int BinNum = BINNUM + 2;

        double *his = new double[BinNum];
        double TempCost;
        int    TempSign;

        *MinCriterion = 9999;

        for (i=0; i<usedFeaCount; i++)
        {
                // build the histogram ...
                memset(his, 0, BinNum * sizeof(double));

                for (j=0; j<TotalSampleNum; j++)
                {
                        //			if (pSampleFlag[j] == 1)
                        {
                                his[FeaValue[i][j]] += (Label[j] == 1 ? Weight[j] : -Weight[j]); 
                        }
                }

                for (j=1; j<BinNum; j++)
                {
                        his[j] += his[j-1];
                }
                for (j=0; j<BinNum-1; j++)
                {
                        TempCost = his[j] + his[j] - his[BinNum-1];
                        TempSign = -1;
                        TempCost = -TempCost;
                        TempCost = (1 + TempCost) / 2.0;
                        if (TempCost > 0.5)
                        {
                                TempCost = 1 - TempCost;
                                TempSign = -TempSign;
                        }
                        if (TempCost < *MinCriterion)
                        {
                                *MinCriterion = TempCost;
                                *SelectedFeaNo = i;

                                // the bin with the minimum error
                                *MinThreshold = j + 1;
                                *MinSign = TempSign;
                        }
                }
        }

        delete []his;
        his = NULL;
}

///////////////////////////////////////////////////////////////////////
inline int Boosting::GetFeatureValue(int DataNo, int FeaNo)
{
        return (FeaValue[FeaNo][DataNo]);
}

///////////////////////////////////////////////////////////////////////
int Boosting::SimpleDiscretClassify(int DataNo, int iteration)
{
        /*	double  rawFeature;
        rawFeature = GetRawFeaValue( SelectedFea[iteration], 
        GetFeatureValue(DataNo, SelectedFea[iteration]) );
        double  rawThreshold;
        rawThreshold = GetRawFeaValue( SelectedFea[iteration], 
        DiscretThreshold[iteration] );
        */
        int value = ( GetFeatureValue(DataNo, SelectedFea[iteration]) -
                DiscretThreshold[iteration] ) 
                * Sign[iteration];

        if (value > 0) 
                return 1;
        else 
                return 0;
}

/////////////////////////////////////////////////////////////////////
int Boosting::StrongDiscretClassify (int DataNo, double tempThreshold)
{
        double s = 0;

        for (int i=0; i<WeakLearnerNum; i++)
        {
                s += apha[i] * ( SimpleDiscretClassify(DataNo,i)==1 );
        }

        return (s >= tempThreshold ? 1 : 0);
}

/////////////////////////////////////////////////////////////////////////////////////
void Boosting::CheckAccuracy(double *Accuracy, double *FalseAlarm, double tempThreshold)
{
        int CorrectPositiveNum = 0;
        int CorrectNegativeNum = 0;

        for (int i=0; i<TotalSampleNum; i++)
        {
                if ( (StrongDiscretClassify(i,tempThreshold) == Label[i]) )
                {
                        CorrectPositiveNum += (Label[i]==1);
                        CorrectNegativeNum += (Label[i]==0);
                }	
        }
        *Accuracy = double(CorrectPositiveNum) / double(PositiveNum);
        *FalseAlarm = 1 - double(CorrectNegativeNum) / double(NegativeNum);

}

////////////////////////////////////////////////////////////////////////////
void Boosting::CheckAccuracyWithVotedValue(double *Accuracy, double tempThreshold)
{
        int CorrectPositiveNum = 0;

        for (int i=0; i<TotalSampleNum; i++)
        {
                //		if (pSampleFlag[i] == 0) continue;
                if ( (Label[i] == 1) && (VotedValue[i] >= tempThreshold) )
                {
                        CorrectPositiveNum += 1;			
                }
        }
        *Accuracy = double(CorrectPositiveNum) / double(PositiveNum);	
}

//////////////////////////////////////////////////////////////////////////////
void Boosting::CheckFalseAlarmWithVotedValue(double *FalseAlarm, double tempThreshold)
{
        int CorrectNegativeNum = 0;

        for (int i=0; i<TotalSampleNum; i++)
        {
                //		if (pSampleFlag[i] == 0) continue;
                if ( (Label[i] == 0) && (VotedValue[i] < tempThreshold) )
                {
                        CorrectNegativeNum += 1;
                }
        }
        *FalseAlarm = 1 - double(CorrectNegativeNum) / double(curNegNum);
}

///////////////////////////////////////////////////////////////////////////////
void Boosting::AdjustThrehold(double AccuracyWanted, double FalseAlarmWanted,
                              double *PresentAccuracy0, double *PresentFalseAlarm0,
                              double *PresentAccuracy, double *PresentFalseAlarm,
                              double *ThresholdWanted)
{
        const int MaxCount = 200;
        double MaxErrorRate = 0 / double(PositiveNum);
        double threshold;
        double threshold2 = FinalThreshold * 5;
        double threshold1 = 0;
        int count;

        CheckAccuracyWithVotedValue(PresentAccuracy0, FinalThreshold);
        CheckFalseAlarmWithVotedValue(PresentFalseAlarm0, FinalThreshold);
        printf("Detection Rate = %lf    False Alarm Rate = %lf\n",*PresentAccuracy0,*PresentFalseAlarm0);		

        *PresentAccuracy = 0;
        *PresentFalseAlarm = 1.0;
        *ThresholdWanted = FinalThreshold;
        count = 0;

        while ( ( (*PresentAccuracy < AccuracyWanted)
                || (*PresentFalseAlarm - 0.0000001 > FalseAlarmWanted)
                ) && (count <= MaxCount) )
        {
                count++;

                threshold = (threshold1 + threshold2) / 2.0;

                CheckAccuracyWithVotedValue(PresentAccuracy, threshold);
                CheckFalseAlarmWithVotedValue(PresentFalseAlarm, threshold);

                if (*PresentAccuracy >= AccuracyWanted)
                {
                        *ThresholdWanted = threshold;
                        threshold1 = threshold;	
                }
                else
                {
                        threshold2 = threshold;
                }
        }

        CheckAccuracyWithVotedValue(PresentAccuracy, *ThresholdWanted);
        CheckFalseAlarmWithVotedValue(PresentFalseAlarm, *ThresholdWanted);
}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -