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

📄 preprocess.c

📁 添加系统调用。。。在LINUX下添加一个新的系统调用。在文件中添加自己的系统调用的源代码
💻 C
字号:
/*cellwriter -- a character recognition input methodCopyright (C) 2007 Michael Levin <risujin@risujin.org>This program is free software; you can redistribute it and/ormodify it under the terms of the GNU General Public Licenseas published by the Free Software Foundation; either version 2of the License, or (at your option) any later version.This program is distributed in the hope that it will be useful,but WITHOUT ANY WARRANTY; without even the implied warranty ofMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See theGNU General Public License for more details.You should have received a copy of the GNU General Public Licensealong with this program; if not, write to the Free SoftwareFoundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, USA.*/#include "config.h"#include "common.h"#include "recognize.h"#include <string.h>/*        Preprocessing engine*//* Maximum and variable versions of the number of samples to prepare for   thorough examination */#define PREP_MAX     (SAMPLES_MAX * 4)#define PREP_SAMPLES (samples_max * 4)/* Greedy mapping */#define VALUE_MAX 2048.f#define VALUE_MIN 1024.f/* Penalties (proportion of final score deducted) */#define VERTICAL_PENALTY 16.00f#define GLUABLE_PENALTY   0.08f#define GLUE_PENALTY      0.02fint ignore_stroke_dir = TRUE, ignore_stroke_num = TRUE, prep_examined;static float measure_partial(Stroke *as, Stroke *b, Vec2 *offset, float scale_b){        Stroke *bs;        float value;        int b_len, min_len;        b_len = b->distance * scale_b / ROUGH_RESOLUTION + 0.5;        if (b_len < 4)                b_len = 4;        min_len = as->len >= b_len ? b_len : as->len;        bs = sample_stroke(NULL, b, b_len, min_len);        value = measure_strokes(as, bs, (MeasureFunc)measure_distance, offset,                                min_len, ROUGH_ELASTICITY);        stroke_free(bs);        return value;}static float greedy_map(Sample *larger, Sample *smaller, Transform *ptfm,                        Vec2 *offset){        Transform tfm;        int i, unmapped_len;        float total;        unmapped_len = larger->len;        /* Prepare transform structure */        memset(&tfm, 0, sizeof (tfm));        *ptfm = tfm;        tfm.valid = TRUE;        for (i = 0, total = 0.f; i < smaller->len; i++) {                float best, best_reach = G_MAXFLOAT, best_value = G_MAXFLOAT,                      value, penalty = G_MAXFLOAT, seg_dist = 0.f;                int j, last_j = 0, best_j = 0, glue = 0;        glue_more:                for (j = 0, best = G_MAXFLOAT; j < larger->len; j++) {                        Stroke *stroke;                        float reach, scale;                        unsigned char gluable;                        if (tfm.order[j])                                continue;                        tfm.reverse[j] = FALSE;                        /* Do not glue on oversize segments */                        if (seg_dist +                            larger->strokes[j]->distance / 2 >                            smaller->strokes[i]->distance &&                            (larger->strokes[j]->spread > DOT_SPREAD ||                             smaller->strokes[i]->spread > DOT_SPREAD))                                continue;                        tfm.order[j] = i + 1;                        tfm.glue[j] = glue;                measure:                        reach = 0.f;                        gluable = 0;                        if (glue) {                                Vec2 v;                                Point *p1, *p2;                                unsigned char gluable2;                                /* Can we glue these strokes together? */                                if (!tfm.reverse[j]) {                                        gluable = larger->strokes[j]->                                                  gluable_start[last_j];                                        gluable2 = larger->strokes[last_j]->                                                   gluable_end[j];                                        if (gluable2 < gluable)                                                gluable = gluable2;                                        if (gluable >= GLUABLE_MAX) {                                                if (!ignore_stroke_dir)                                                        continue;                                                tfm.reverse[j] = TRUE;                                        }                                }                                if (tfm.reverse[j]) {                                        gluable = larger->strokes[j]->                                                  gluable_end[last_j];                                        gluable2 = larger->strokes[last_j]->                                                   gluable_start[j];                                        if (gluable2 < gluable)                                                gluable = gluable2;                                        if (gluable >= GLUABLE_MAX)                                                continue;                                }                                /* Get the inter-stroke (reach) distance */                                p1 = larger->strokes[last_j]->points +                                     (tfm.reverse[last_j] ? 0 :                                      larger->strokes[last_j]->len - 1);                                p2 = larger->strokes[j]->points +                                     (!tfm.reverse[j] ? 0 :                                      larger->strokes[j]->len - 1);                                vec2_set(&v, p2->x - p1->x,                                         p2->y - p1->y);                                reach = vec2_mag(&v);                        }                        /* Transform and measure the distance */                        stroke = transform_stroke(larger, &tfm, i);                        scale = smaller->distance /                                (reach + ptfm->reach + larger->distance);                        value = measure_partial(smaller->roughs[i], stroke,                                                offset, scale);                        /* Keep track of the best result */                        if (value < best && value < VALUE_MAX) {                                best = value;                                best_j = j;                                best_reach = reach;                                *ptfm = tfm;                                /* Penalize glue and reach distance */                                penalty = glue * GLUE_PENALTY +                                          gluable * GLUABLE_PENALTY /                                                    GLUABLE_MAX;                        }                        stroke_free(stroke);                        /* Bail if we have a really good match */                        if (value < VALUE_MIN)                                break;                        /* Glue on with reversed direction */                        if (ignore_stroke_dir && !tfm.reverse[j] &&                            larger->strokes[j]->spread > DOT_SPREAD) {                                tfm.reverse[j] = TRUE;                                goto measure;                        }                        tfm.reverse[j] = FALSE;                        tfm.order[j] = 0;                }                if (best < G_MAXFLOAT) {                        best_value = best;                        larger->penalty += penalty;                        smaller->penalty += penalty;                        seg_dist += best_reach +                                    larger->strokes[best_j]->distance;                        ptfm->reach += best_reach;                        tfm = *ptfm;                        /* If we still have strokes and we didn't just add on                           a dot, try gluing them on */                        unmapped_len--;                        if (unmapped_len >= smaller->len - i &&                            larger->strokes[best_j]->spread >                            DOT_SPREAD) {                                last_j = best_j;                                glue++;                                goto glue_more;                        }                }                /* Didn't map a target stroke? */                else if (!glue) {                        ptfm->valid = FALSE;                        return G_MAXFLOAT;                }                total += best_value;        }        /* Didn't assign all of the strokes? */        if (unmapped_len) {                ptfm->valid = FALSE;                return G_MAXFLOAT;        }        return total / smaller->len;}static int prep_sample(Sample *sample){        Vec2 offset;        float dist;        /* Structural disqualification */        if (!sample->used || !sample->enabled ||            (!ignore_stroke_num && sample->len != input->len))                return FALSE;        prep_examined++;        sample->penalty = 0.f;        /* Account for displacement */        center_samples(&offset, sample, input);        /* Compare each input stroke to every stroke in the sample and           generate the stroke order information which will be used by other           engines */        if (input->len >= sample->len)                dist = greedy_map(input, sample, &sample->transform, &offset);        else {                vec2_set(&offset, -offset.x, -offset.y);                dist = greedy_map(sample, input, &sample->transform, &offset);        }        if (!sample->transform.valid)                return FALSE;        /* Undo square distortion */        dist = sqrtf(dist);        if (dist > MAX_DIST)                return FALSE;        /* Penalize vertical displacement */        sample->penalty += VERTICAL_PENALTY *                           offset.y * offset.y / SCALE / SCALE;        sample->ratings[ENGINE_PREP] = RATING_MAX -                                       RATING_MAX * dist / MAX_DIST;        return TRUE;}void engine_prep(void){        Sample *sample, *list[PREP_MAX];        int i;        /* Rate every sample in every possible configuration */        list[0] = NULL;        prep_examined = 0;        sampleiter_reset();        while ((sample = sampleiter_next())) {                sample->disqualified = TRUE;                if (!sample->used || !sample->ch || !prep_sample(sample))                        continue;                /* Bubble-sort sample into the list */                for (i = 0; i < PREP_SAMPLES; i++)                        if (!list[i]) {                                list[i] = sample;                                if (i < PREP_MAX - 1)                                        list[i + 1] = NULL;                                break;                        } else if (list[i]->ratings[ENGINE_PREP] <                                   sample->ratings[ENGINE_PREP]) {                                memmove(list + i + 1, list + i,                                        (PREP_MAX - i - 1) * sizeof (*list));                                list[i] = sample;                                break;                        }        }        /* Qualify the best samples */        for (i = 0; i < PREP_SAMPLES && list[i]; i++)                list[i]->disqualified = FALSE;}

⌨️ 快捷键说明

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