ターゲット検出データベースPASCAL形式のGround Truthの解析関数

14350 ワード

最近、目標検出アルゴリズムを作成し、訓練時にbootstrapポリシーを使用したので、PASCALのGround Truth形式の読み取り関数をMatlabからC++に書き換えました.PASCALの表記形式は次のとおりです.
# PASCAL Annotation Version 1.00
Image filename : "      "
Image size (X x Y x C) : x x 3
Database : " "
Objects with ground truth : 1 { "PASperson" }
# Note that there might be other objects in the image
# for which ground truth data has not been provided.
# Top left pixel co-ordinates : (0, 0)
# Details for object 1 ("PASperson")
# Center point -- not available in other PASCAL databases -- refers
# to person head center
Original label for object 1 "PASperson" : "UprightPerson"
Center point on object 1 "PASperson" (X, Y) : (257, 187)
Bounding box for object 1 "PASperson" (Xmin, Ymin) - (Xmax, Ymax) : (195, 154) - (297, 468)

私が書いた関数は次のとおりです.
#include "stdio.h"

#include "string.h"

#include "stdlib.h"



// object bounding rect

struct GtRect {

    int x_min; int y_min;

    int x_max; int y_max; 

};



// ground truth of one image

struct GtRecord {

    char* image_name;

    GtRect* objs;

    int obj_num; int height;

    int width; int channels;

};



// return true if c is in char set s

int _is_chars(char c, const char* s, int n)

{

    for (int i = 0; i != n; ++i) {

        if (s[i] == c) {

            return 1;

        }

    }

    return 0;

}



void _trim_l(char* inout, const char* s)

{

    int len = strlen(inout);

    int s_len = strlen(s);

    int i = 0;

    for (;i != len; ++i) {

        if (!_is_chars(inout[i], s, s_len)) {

            break;

        }

    }

    int d = i;

    int new_len = len - d;

    for (i = 0; i != new_len; ++i) {

        inout[i] = inout[i + d];

    }

    inout[new_len] = '\0';

}



void _trim_r(char* inout, const char* s)

{

    int len = strlen(inout);

    int s_len = strlen(s);

    int i = len - 1;

    for (;i != -1; --i) {

        if (!_is_chars(inout[i], s, s_len)) {

            break;

        }

    }

    inout[i + 1] = '\0';

}



inline void _trim_lr(char* inout, const char* s)

{

    _trim_l(inout, s);

    _trim_r(inout, s);

}



// read ground truth (pascal format)

//************************************

// Name:  gt_pascal_read

// Returns:   GtRecord

// const char * path    :    groundtruth file path

//************************************

GtRecord gt_pascal_read(const char* path)

{

    GtRecord ret = {0, 0, 0, 0, 0, 0};

    FILE* f;

    fopen_s(&f, path, "r");

    int obj_num = 0;

    int len = 0;

    GtRect rct;

    while (fgets(BUF1, 5000, f) != 0) {

        int match_type = _match_attr(BUF1);

        switch (match_type) {

        case 0:

            // read image filename

            sscanf_s(BUF1, _GT_ATTR[0], BUF2, 500);

            _trim_lr(BUF2, "
\"
"); len = strlen(BUF2); ret.image_name = (char*)malloc(len + 1); memcpy(ret.image_name, BUF2, len + 1); break; case 1: // read image size, channel sscanf_s(BUF1, _GT_ATTR[1], &ret.width, &ret.height, &ret.channels); break; case 2: // ignore database name break; case 3: sscanf_s(BUF1, _GT_ATTR[3], &rct.x_min, &rct.y_min, &rct.x_max, &rct.y_max); OBJ_BUF[obj_num++] = rct; break; case 4: // ignore polygon case 5: // ignore pixel map case 6: // ignore label break; } } fclose(f); ret.obj_num = obj_num; if (obj_num > 0) { ret.objs = (GtRect*)malloc(sizeof(GtRect) * obj_num); memcpy(ret.objs, OBJ_BUF, obj_num * sizeof(GtRect)); } return ret; } // release pascal ground truth //************************************ // Name: gt_pascal_release // Returns: void // GtRecord * r //************************************ void gt_pascal_release(GtRecord* r) { free(r->image_name); free(r->objs); r->image_name = 0; r->objs = 0; r->width = 0; r->height = 0; r->channels = 0; r->obj_num = 0; }

gt_pascal_read関数はgroundtruthファイルのデータベース名などの属性を無視し、戻す場合は関数のいくつかの空のcaseに追加できます.PASCALは、このようなgroundtruthファイルを読み取り、生成するためにいくつかの有用なMatlabスクリプトを公式に提供しており、アルゴリズム開発の過程でこのようなツールを多く利用しなければならない.