mirror of
https://github.com/tesseract-ocr/tesseract.git
synced 2025-01-18 06:30:14 +08:00
Merge pull request #1705 from stweil/memory
Replace proprietary memory allocators from memry.c, memry.h
This commit is contained in:
commit
a9369ffa48
@ -21,7 +21,6 @@
|
||||
#include <ctype.h>
|
||||
#include <cstring>
|
||||
#include "tessvars.h"
|
||||
#include "memry.h"
|
||||
#include "reject.h"
|
||||
#include "control.h"
|
||||
#include "stopper.h"
|
||||
|
@ -24,16 +24,15 @@
|
||||
#include "config_auto.h"
|
||||
#endif
|
||||
|
||||
#include "stderr.h"
|
||||
#include "basedir.h"
|
||||
#include "tessvars.h"
|
||||
#include "control.h"
|
||||
#include "reject.h"
|
||||
#include "pageres.h"
|
||||
#include "nwmain.h"
|
||||
#include "pgedit.h"
|
||||
#include "tprintf.h"
|
||||
#include "tessedit.h"
|
||||
#include "basedir.h"
|
||||
#include "tessvars.h"
|
||||
#include "control.h"
|
||||
#include "reject.h"
|
||||
#include "pageres.h"
|
||||
#include "nwmain.h"
|
||||
#include "pgedit.h"
|
||||
#include "tprintf.h"
|
||||
#include "tessedit.h"
|
||||
#include "stopper.h"
|
||||
#include "intmatcher.h"
|
||||
#include "chop.h"
|
||||
|
@ -64,8 +64,7 @@ C_OUTLINE::C_OUTLINE(CRACKEDGE* startpt, ICOORD bot_left, ICOORD top_right,
|
||||
return;
|
||||
}
|
||||
//get memory
|
||||
steps = (uint8_t *) alloc_mem (step_mem());
|
||||
memset(steps, 0, step_mem());
|
||||
steps = (uint8_t *)calloc(step_mem(), 1);
|
||||
edgept = startpt;
|
||||
|
||||
for (stepindex = 0; stepindex < length; stepindex++) {
|
||||
@ -98,8 +97,7 @@ int16_t length //length of loop
|
||||
pos = startpt;
|
||||
stepcount = length; // No. of steps.
|
||||
ASSERT_HOST(length >= 0);
|
||||
steps = static_cast<uint8_t*>(alloc_mem(step_mem())); // Get memory.
|
||||
memset(steps, 0, step_mem());
|
||||
steps = static_cast<uint8_t*>(calloc(step_mem(), 1)); // Get memory.
|
||||
|
||||
lastdir = new_steps[length - 1];
|
||||
prevdir = lastdir;
|
||||
@ -162,8 +160,7 @@ C_OUTLINE::C_OUTLINE(C_OUTLINE* srcline, FCOORD rotation) : offsets(nullptr) {
|
||||
return;
|
||||
}
|
||||
//get memory
|
||||
steps = (uint8_t *) alloc_mem (step_mem());
|
||||
memset(steps, 0, step_mem());
|
||||
steps = (uint8_t *)calloc(step_mem(), 1);
|
||||
|
||||
for (int iteration = 0; iteration < 2; ++iteration) {
|
||||
DIR128 round1 = iteration == 0 ? 32 : 0;
|
||||
@ -1014,10 +1011,9 @@ void C_OUTLINE::plot_normed(const DENORM& denorm, ScrollView::Color colour,
|
||||
C_OUTLINE& C_OUTLINE::operator=(const C_OUTLINE& source) {
|
||||
box = source.box;
|
||||
start = source.start;
|
||||
if (steps != nullptr)
|
||||
free_mem(steps);
|
||||
free(steps);
|
||||
stepcount = source.stepcount;
|
||||
steps = (uint8_t *) alloc_mem (step_mem());
|
||||
steps = (uint8_t *)malloc(step_mem());
|
||||
memmove (steps, source.steps, step_mem());
|
||||
if (!children.empty ())
|
||||
children.clear ();
|
||||
|
@ -24,7 +24,6 @@
|
||||
#include "bits16.h" // for BITS16
|
||||
#include "elst.h" // for ELIST_ITERATOR, ELISTIZEH, ELIST_LINK
|
||||
#include "ipoints.h" // for operator+=
|
||||
#include "memry.h" // for free_mem
|
||||
#include "mod128.h" // for DIR128, DIRBITS
|
||||
#include "platform.h" // for DLLSYM
|
||||
#include "points.h" // for ICOORD, FCOORD
|
||||
@ -92,9 +91,7 @@ class DLLSYM C_OUTLINE:public ELIST_LINK {
|
||||
static void FakeOutline(const TBOX& box, C_OUTLINE_LIST* outlines);
|
||||
|
||||
~C_OUTLINE () { //destructor
|
||||
if (steps != nullptr)
|
||||
free_mem(steps);
|
||||
steps = nullptr;
|
||||
free(steps);
|
||||
delete [] offsets;
|
||||
}
|
||||
|
||||
@ -286,9 +283,9 @@ class DLLSYM C_OUTLINE:public ELIST_LINK {
|
||||
|
||||
TBOX box; // bounding box
|
||||
ICOORD start; // start coord
|
||||
int16_t stepcount; // no of steps
|
||||
int16_t stepcount; // no of steps
|
||||
BITS16 flags; // flags about outline
|
||||
uint8_t *steps; // step array
|
||||
uint8_t *steps; // step array
|
||||
EdgeOffset* offsets; // Higher precision edge.
|
||||
C_OUTLINE_LIST children; // child elements
|
||||
static ICOORD step_coords[4];
|
||||
|
@ -18,7 +18,6 @@
|
||||
**********************************************************************/
|
||||
|
||||
#include "allheaders.h"
|
||||
#include "memry.h"
|
||||
#include "quadlsq.h"
|
||||
#include "quspline.h"
|
||||
|
||||
@ -43,8 +42,8 @@ QSPLINE::QSPLINE( //constructor
|
||||
int32_t index; //segment index
|
||||
|
||||
//get memory
|
||||
xcoords = (int32_t *) alloc_mem ((count + 1) * sizeof (int32_t));
|
||||
quadratics = (QUAD_COEFFS *) alloc_mem (count * sizeof (QUAD_COEFFS));
|
||||
xcoords = new int32_t[count + 1];
|
||||
quadratics = new QUAD_COEFFS[count];
|
||||
segments = count;
|
||||
for (index = 0; index < segments; index++) {
|
||||
//copy them
|
||||
@ -77,9 +76,9 @@ int degree //fit required
|
||||
QLSQ qlsq; /*accumulator */
|
||||
|
||||
segments = segcount;
|
||||
xcoords = (int32_t *) alloc_mem ((segcount + 1) * sizeof (int32_t));
|
||||
ptcounts = (int32_t *) alloc_mem ((segcount + 1) * sizeof (int32_t));
|
||||
quadratics = (QUAD_COEFFS *) alloc_mem (segcount * sizeof (QUAD_COEFFS));
|
||||
xcoords = new int32_t[segcount + 1];
|
||||
ptcounts = new int32_t[segcount + 1];
|
||||
quadratics = new QUAD_COEFFS[segcount];
|
||||
memmove (xcoords, xstarts, (segcount + 1) * sizeof (int32_t));
|
||||
ptcounts[0] = 0; /*none in any yet */
|
||||
for (segment = 0, pointindex = 0; pointindex < pointcount; pointindex++) {
|
||||
@ -123,7 +122,7 @@ int degree //fit required
|
||||
quadratics[segment].b = qlsq.get_b ();
|
||||
quadratics[segment].c = qlsq.get_c ();
|
||||
}
|
||||
free_mem(ptcounts);
|
||||
delete[] ptcounts;
|
||||
}
|
||||
|
||||
|
||||
@ -148,16 +147,9 @@ QSPLINE::QSPLINE( //constructor
|
||||
* Destroy a QSPLINE.
|
||||
**********************************************************************/
|
||||
|
||||
QSPLINE::~QSPLINE ( //constructor
|
||||
) {
|
||||
if (xcoords != nullptr) {
|
||||
free_mem(xcoords);
|
||||
xcoords = nullptr;
|
||||
}
|
||||
if (quadratics != nullptr) {
|
||||
free_mem(quadratics);
|
||||
quadratics = nullptr;
|
||||
}
|
||||
QSPLINE::~QSPLINE () {
|
||||
delete[] xcoords;
|
||||
delete[] quadratics;
|
||||
}
|
||||
|
||||
|
||||
@ -169,14 +161,12 @@ QSPLINE::~QSPLINE ( //constructor
|
||||
|
||||
QSPLINE & QSPLINE::operator= ( //assignment
|
||||
const QSPLINE & source) {
|
||||
if (xcoords != nullptr)
|
||||
free_mem(xcoords);
|
||||
if (quadratics != nullptr)
|
||||
free_mem(quadratics);
|
||||
delete[] xcoords;
|
||||
delete[] quadratics;
|
||||
|
||||
segments = source.segments;
|
||||
xcoords = (int32_t *) alloc_mem ((segments + 1) * sizeof (int32_t));
|
||||
quadratics = (QUAD_COEFFS *) alloc_mem (segments * sizeof (QUAD_COEFFS));
|
||||
xcoords = new int32_t[segments + 1];
|
||||
quadratics = new QUAD_COEFFS[segments];
|
||||
memmove (xcoords, source.xcoords, (segments + 1) * sizeof (int32_t));
|
||||
memmove (quadratics, source.quadratics, segments * sizeof (QUAD_COEFFS));
|
||||
return *this;
|
||||
@ -303,7 +293,7 @@ void QSPLINE::extrapolate( //linear extrapolation
|
||||
) {
|
||||
int segment; /*current segment of spline */
|
||||
int dest_segment; //dest index
|
||||
int *xstarts; //new boundaries
|
||||
int32_t* xstarts; //new boundaries
|
||||
QUAD_COEFFS *quads; //new ones
|
||||
int increment; //in size
|
||||
|
||||
@ -312,9 +302,8 @@ void QSPLINE::extrapolate( //linear extrapolation
|
||||
increment++;
|
||||
if (increment == 0)
|
||||
return;
|
||||
xstarts = (int *) alloc_mem ((segments + 1 + increment) * sizeof (int));
|
||||
quads =
|
||||
(QUAD_COEFFS *) alloc_mem ((segments + increment) * sizeof (QUAD_COEFFS));
|
||||
xstarts = new int32_t[segments + 1 + increment];
|
||||
quads = new QUAD_COEFFS[segments + increment];
|
||||
if (xmin < xcoords[0]) {
|
||||
xstarts[0] = xmin;
|
||||
quads[0].a = 0;
|
||||
@ -339,9 +328,9 @@ void QSPLINE::extrapolate( //linear extrapolation
|
||||
xstarts[dest_segment] = xmax + 1;
|
||||
}
|
||||
segments = dest_segment;
|
||||
free_mem(xcoords);
|
||||
free_mem(quadratics);
|
||||
xcoords = (int32_t *) xstarts;
|
||||
delete[] xcoords;
|
||||
delete[] quadratics;
|
||||
xcoords = xstarts;
|
||||
quadratics = quads;
|
||||
}
|
||||
|
||||
|
@ -1,8 +1,8 @@
|
||||
/**********************************************************************
|
||||
* File: quspline.h (Formerly qspline.h)
|
||||
* Description: Code for the QSPLINE class.
|
||||
* Author: Ray Smith
|
||||
* Created: Tue Oct 08 17:16:12 BST 1991
|
||||
* Author: Ray Smith
|
||||
* Created: Tue Oct 08 17:16:12 BST 1991
|
||||
*
|
||||
* (C) Copyright 1991, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
@ -17,13 +17,12 @@
|
||||
*
|
||||
**********************************************************************/
|
||||
|
||||
#ifndef QUSPLINE_H
|
||||
#define QUSPLINE_H
|
||||
#ifndef QUSPLINE_H
|
||||
#define QUSPLINE_H
|
||||
|
||||
#include "quadratc.h"
|
||||
#include "serialis.h"
|
||||
#include "memry.h"
|
||||
#include "rect.h"
|
||||
#include "quadratc.h"
|
||||
#include "serialis.h"
|
||||
#include "rect.h"
|
||||
|
||||
class ROW;
|
||||
struct Pix;
|
||||
|
@ -19,8 +19,8 @@ pkginclude_HEADERS = \
|
||||
noinst_HEADERS = \
|
||||
ambigs.h basedir.h bits16.h bitvector.h ccutil.h clst.h doubleptr.h elst2.h \
|
||||
elst.h errcode.h fileerr.h genericheap.h globaloc.h \
|
||||
indexmapbidi.h kdpair.h lsterr.h memry.h \
|
||||
nwmain.h object_cache.h params.h qrsequence.h sorthelper.h stderr.h \
|
||||
indexmapbidi.h kdpair.h lsterr.h \
|
||||
nwmain.h object_cache.h params.h qrsequence.h sorthelper.h \
|
||||
scanutils.h tessdatamanager.h tprintf.h \
|
||||
unicharcompress.h unicharmap.h unicharset.h unicity_table.h unicodes.h \
|
||||
universalambigs.h
|
||||
@ -32,7 +32,7 @@ libtesseract_ccutil_la_SOURCES = \
|
||||
ccutil.cpp clst.cpp \
|
||||
elst2.cpp elst.cpp errcode.cpp \
|
||||
globaloc.cpp indexmapbidi.cpp \
|
||||
mainblk.cpp memry.cpp \
|
||||
mainblk.cpp \
|
||||
serialis.cpp strngs.cpp scanutils.cpp \
|
||||
tessdatamanager.cpp tprintf.cpp \
|
||||
unichar.cpp unicharcompress.cpp unicharmap.cpp unicharset.cpp unicodes.cpp \
|
||||
|
@ -1,45 +0,0 @@
|
||||
/**********************************************************************
|
||||
* File: memry.cpp (Formerly memory.c)
|
||||
* Description: Memory allocation with builtin safety checks.
|
||||
* Author: Ray Smith
|
||||
* Created: Wed Jan 22 09:43:33 GMT 1992
|
||||
*
|
||||
* (C) Copyright 1992, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
** you may not use this file except in compliance with the License.
|
||||
** You may obtain a copy of the License at
|
||||
** http://www.apache.org/licenses/LICENSE-2.0
|
||||
** Unless required by applicable law or agreed to in writing, software
|
||||
** distributed under the License is distributed on an "AS IS" BASIS,
|
||||
** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
** See the License for the specific language governing permissions and
|
||||
** limitations under the License.
|
||||
*
|
||||
**********************************************************************/
|
||||
|
||||
#include "memry.h"
|
||||
#include <stdlib.h>
|
||||
|
||||
// With improvements in OS memory allocators, internal memory management
|
||||
// is no longer required, so all these functions now map to their malloc
|
||||
// family equivalents.
|
||||
|
||||
// TODO(rays) further cleanup by redirecting calls to new and creating proper
|
||||
// constructors.
|
||||
|
||||
char *alloc_string(int32_t count) {
|
||||
// Round up the amount allocated to a multiple of 4
|
||||
return static_cast<char*>(malloc((count + 3) & ~3));
|
||||
}
|
||||
|
||||
void free_string(char *string) {
|
||||
free(string);
|
||||
}
|
||||
|
||||
void *alloc_mem(int32_t count) {
|
||||
return malloc(static_cast<size_t>(count));
|
||||
}
|
||||
|
||||
void free_mem(void *oldchunk) {
|
||||
free(oldchunk);
|
||||
}
|
@ -1,34 +0,0 @@
|
||||
/**********************************************************************
|
||||
* File: memry.h (Formerly memory.h)
|
||||
* Description: Header file for basic memory allocation/deallocation.
|
||||
* Author: Ray Smith
|
||||
* Created: Tue May 8 16:03:48 BST 1990
|
||||
*
|
||||
* (C) Copyright 1990, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
** you may not use this file except in compliance with the License.
|
||||
** You may obtain a copy of the License at
|
||||
** http://www.apache.org/licenses/LICENSE-2.0
|
||||
** Unless required by applicable law or agreed to in writing, software
|
||||
** distributed under the License is distributed on an "AS IS" BASIS,
|
||||
** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
** See the License for the specific language governing permissions and
|
||||
** limitations under the License.
|
||||
*
|
||||
**********************************************************************/
|
||||
|
||||
#ifndef MEMRY_H
|
||||
#define MEMRY_H
|
||||
|
||||
#include <cstdint>
|
||||
|
||||
// allocate string
|
||||
extern char *alloc_string(int32_t count);
|
||||
// free a string.
|
||||
extern void free_string(char *string);
|
||||
// get some memory
|
||||
extern void *alloc_mem(int32_t count);
|
||||
// free mem from alloc_mem
|
||||
extern void free_mem(void *oldchunk);
|
||||
|
||||
#endif
|
@ -1,26 +0,0 @@
|
||||
/**********************************************************************
|
||||
* File: stderr.h (Formerly stderrs.h)
|
||||
* Description: File defining error messages fundamental of commonly used.
|
||||
* Author: Ray Smith
|
||||
* Created: Fri Aug 10 15:23:14 BST 1990
|
||||
*
|
||||
* (C) Copyright 1990, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
** you may not use this file except in compliance with the License.
|
||||
** You may obtain a copy of the License at
|
||||
** http://www.apache.org/licenses/LICENSE-2.0
|
||||
** Unless required by applicable law or agreed to in writing, software
|
||||
** distributed under the License is distributed on an "AS IS" BASIS,
|
||||
** WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
** See the License for the specific language governing permissions and
|
||||
** limitations under the License.
|
||||
*
|
||||
**********************************************************************/
|
||||
|
||||
#ifndef STDERR_H
|
||||
#define STDERR_H
|
||||
|
||||
#include "errcode.h"
|
||||
|
||||
const ERRCODE MEMORY_OUT = "Out of memory";
|
||||
#endif
|
@ -19,10 +19,10 @@
|
||||
|
||||
#include "strngs.h"
|
||||
#include <cassert> // for assert
|
||||
#include <cstdlib> // for malloc, free
|
||||
#include "errcode.h" // for ASSERT_HOST
|
||||
#include "genericvector.h" // for GenericVector
|
||||
#include "helpers.h" // for ReverseN
|
||||
#include "memry.h" // for alloc_string, free_string
|
||||
#include "serialis.h" // for TFile
|
||||
|
||||
using tesseract::TFile;
|
||||
@ -51,7 +51,7 @@ const int kMaxDoubleSize = 16;
|
||||
const int kMinCapacity = 16;
|
||||
|
||||
char* STRING::AllocData(int used, int capacity) {
|
||||
data_ = (STRING_HEADER *)alloc_string(capacity + sizeof(STRING_HEADER));
|
||||
data_ = (STRING_HEADER *)malloc(capacity + sizeof(STRING_HEADER));
|
||||
|
||||
// header is the metadata for this memory block
|
||||
STRING_HEADER* header = GetHeader();
|
||||
@ -61,7 +61,8 @@ char* STRING::AllocData(int used, int capacity) {
|
||||
}
|
||||
|
||||
void STRING::DiscardData() {
|
||||
free_string((char *)data_);
|
||||
free(data_);
|
||||
data_ = nullptr;
|
||||
}
|
||||
|
||||
// This is a private method; ensure FixHeader is called (or used_ is well defined)
|
||||
@ -78,7 +79,7 @@ char* STRING::ensure_cstr(int32_t min_capacity) {
|
||||
min_capacity = 2 * orig_header->capacity_;
|
||||
|
||||
int alloc = sizeof(STRING_HEADER) + min_capacity;
|
||||
STRING_HEADER* new_header = (STRING_HEADER*)(alloc_string(alloc));
|
||||
STRING_HEADER* new_header = (STRING_HEADER*)(malloc(alloc));
|
||||
|
||||
memcpy(&new_header[1], GetCStr(), orig_header->used_);
|
||||
new_header->capacity_ = min_capacity;
|
||||
|
@ -1,8 +1,8 @@
|
||||
/**********************************************************************
|
||||
* File: fpchop.cpp (Formerly fp_chop.c)
|
||||
* Description: Code to chop fixed pitch text into character cells.
|
||||
* Author: Ray Smith
|
||||
* Created: Thu Sep 16 11:14:15 BST 1993
|
||||
* Author: Ray Smith
|
||||
* Created: Thu Sep 16 11:14:15 BST 1993
|
||||
*
|
||||
* (C) Copyright 1993, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
@ -17,7 +17,6 @@
|
||||
*
|
||||
**********************************************************************/
|
||||
|
||||
#include "stderr.h"
|
||||
#include "blobbox.h"
|
||||
#include "statistc.h"
|
||||
#include "drawtord.h"
|
||||
|
@ -7,8 +7,9 @@
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
#include "statistc.h"
|
||||
#include "gap_map.h"
|
||||
|
||||
#include "statistc.h"
|
||||
#include "gap_map.h"
|
||||
|
||||
#define EXTERN
|
||||
EXTERN BOOL_VAR (gapmap_debug, FALSE, "Say which blocks have tables");
|
||||
@ -79,7 +80,7 @@ GAPMAP::GAPMAP( //Constructor
|
||||
}
|
||||
bucket_size = (int16_t) floor (xht_stats.median () + 0.5) / 2;
|
||||
map_max = (max_right - min_left) / bucket_size;
|
||||
map = (int16_t *) alloc_mem ((map_max + 1) * sizeof (int16_t));
|
||||
map = new int16_t[map_max + 1];
|
||||
for (i = 0; i <= map_max; i++)
|
||||
map[i] = 0;
|
||||
|
||||
|
@ -7,10 +7,11 @@
|
||||
// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||
// See the License for the specific language governing permissions and
|
||||
// limitations under the License.
|
||||
#ifndef GAP_MAP_H
|
||||
#define GAP_MAP_H
|
||||
|
||||
#include "blobbox.h"
|
||||
#ifndef GAP_MAP_H
|
||||
#define GAP_MAP_H
|
||||
|
||||
#include "blobbox.h"
|
||||
|
||||
class GAPMAP
|
||||
{
|
||||
@ -19,8 +20,7 @@ class GAPMAP
|
||||
TO_BLOCK *block);
|
||||
|
||||
~GAPMAP () { //destructor
|
||||
if (map != nullptr)
|
||||
free_mem(map);
|
||||
delete[] map;
|
||||
}
|
||||
|
||||
bool table_gap( //Is gap a table?
|
||||
@ -45,4 +45,5 @@ extern BOOL_VAR_H (gapmap_use_ends, FALSE,
|
||||
extern BOOL_VAR_H (gapmap_no_isolated_quanta, FALSE,
|
||||
"Ensure gaps not less than 2quanta wide");
|
||||
extern double_VAR_H (gapmap_big_gaps, 1.75, "xht multiplier");
|
||||
|
||||
#endif
|
||||
|
@ -1,8 +1,8 @@
|
||||
/**********************************************************************
|
||||
* File: makerow.cpp (Formerly makerows.c)
|
||||
* Description: Code to arrange blobs into rows of text.
|
||||
* Author: Ray Smith
|
||||
* Created: Mon Sep 21 14:34:48 BST 1992
|
||||
* Author: Ray Smith
|
||||
* Created: Mon Sep 21 14:34:48 BST 1992
|
||||
*
|
||||
* (C) Copyright 1992, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
@ -17,7 +17,7 @@
|
||||
*
|
||||
**********************************************************************/
|
||||
|
||||
#include "stderr.h"
|
||||
#include <vector> // for std::vector
|
||||
#include "blobbox.h"
|
||||
#include "ccstruct.h"
|
||||
#include "detlinefit.h"
|
||||
@ -288,12 +288,10 @@ void compute_page_skew( //get average gradient
|
||||
float &page_m, //average gradient
|
||||
float &page_err //average error
|
||||
) {
|
||||
int32_t row_count; //total rows
|
||||
int32_t blob_count; //total_blobs
|
||||
int32_t row_err; //integer error
|
||||
float *gradients; //of rows
|
||||
float *errors; //of rows
|
||||
int32_t row_index; //of total
|
||||
int32_t row_count; //total rows
|
||||
int32_t blob_count; //total_blobs
|
||||
int32_t row_err; //integer error
|
||||
int32_t row_index; //of total
|
||||
TO_ROW *row; //current row
|
||||
TO_BLOCK_IT block_it = blocks; //iterator
|
||||
|
||||
@ -315,11 +313,10 @@ void compute_page_skew( //get average gradient
|
||||
page_err = 0.0f;
|
||||
return;
|
||||
}
|
||||
gradients = (float *) alloc_mem (blob_count * sizeof (float));
|
||||
//get mem
|
||||
errors = (float *) alloc_mem (blob_count * sizeof (float));
|
||||
if (gradients == nullptr || errors == nullptr)
|
||||
MEMORY_OUT.error ("compute_page_skew", ABORT, nullptr);
|
||||
// of rows
|
||||
std::vector<float> gradients(blob_count);
|
||||
// of rows
|
||||
std::vector<float> errors(blob_count);
|
||||
|
||||
row_index = 0;
|
||||
for (block_it.mark_cycle_pt (); !block_it.cycled_list ();
|
||||
@ -369,13 +366,11 @@ void compute_page_skew( //get average gradient
|
||||
}
|
||||
row_count = row_index;
|
||||
row_index = choose_nth_item ((int32_t) (row_count * textord_skew_ile),
|
||||
gradients, row_count);
|
||||
&gradients[0], row_count);
|
||||
page_m = gradients[row_index];
|
||||
row_index = choose_nth_item ((int32_t) (row_count * textord_skew_ile),
|
||||
errors, row_count);
|
||||
&errors[0], row_count);
|
||||
page_err = errors[row_index];
|
||||
free_mem(gradients);
|
||||
free_mem(errors);
|
||||
}
|
||||
|
||||
const double kNoiseSize = 0.5; // Fraction of xheight.
|
||||
@ -580,8 +575,6 @@ void delete_non_dropout_rows( //find lines
|
||||
bool testing_on //correct orientation
|
||||
) {
|
||||
TBOX block_box; //deskewed block
|
||||
int32_t *deltas; //change in occupation
|
||||
int32_t *occupation; //of pixel coords
|
||||
int32_t max_y; //in block
|
||||
int32_t min_y;
|
||||
int32_t line_index; //of scan line
|
||||
@ -610,12 +603,12 @@ void delete_non_dropout_rows( //find lines
|
||||
line_count = max_y - min_y + 1;
|
||||
if (line_count <= 0)
|
||||
return; //empty block
|
||||
deltas = (int32_t *) alloc_mem (line_count * sizeof (int32_t));
|
||||
occupation = (int32_t *) alloc_mem (line_count * sizeof (int32_t));
|
||||
if (deltas == nullptr || occupation == nullptr)
|
||||
MEMORY_OUT.error ("compute_line_spacing", ABORT, nullptr);
|
||||
// change in occupation
|
||||
std::vector<int32_t> deltas(line_count);
|
||||
// of pixel coords
|
||||
std::vector<int32_t> occupation(line_count);
|
||||
|
||||
compute_line_occupation(block, gradient, min_y, max_y, occupation, deltas);
|
||||
compute_line_occupation(block, gradient, min_y, max_y, &occupation[0], &deltas[0]);
|
||||
compute_occupation_threshold ((int32_t)
|
||||
ceil (block->line_spacing *
|
||||
(tesseract::CCStruct::kDescenderFraction +
|
||||
@ -623,13 +616,13 @@ void delete_non_dropout_rows( //find lines
|
||||
(int32_t) ceil (block->line_spacing *
|
||||
(tesseract::CCStruct::kXHeightFraction +
|
||||
tesseract::CCStruct::kAscenderFraction)),
|
||||
max_y - min_y + 1, occupation, deltas);
|
||||
max_y - min_y + 1, &occupation[0], &deltas[0]);
|
||||
#ifndef GRAPHICS_DISABLED
|
||||
if (testing_on) {
|
||||
draw_occupation(xleft, ybottom, min_y, max_y, occupation, deltas);
|
||||
draw_occupation(xleft, ybottom, min_y, max_y, &occupation[0], &deltas[0]);
|
||||
}
|
||||
#endif
|
||||
compute_dropout_distances(occupation, deltas, line_count);
|
||||
compute_dropout_distances(&occupation[0], &deltas[0], line_count);
|
||||
for (row_it.mark_cycle_pt (); !row_it.cycled_list (); row_it.forward ()) {
|
||||
row = row_it.data ();
|
||||
line_index = (int32_t) floor (row->intercept ());
|
||||
@ -648,9 +641,6 @@ void delete_non_dropout_rows( //find lines
|
||||
for (row_it.mark_cycle_pt (); !row_it.cycled_list (); row_it.forward ()) {
|
||||
blob_it.add_list_after (row_it.data ()->blob_list ());
|
||||
}
|
||||
|
||||
free_mem(deltas);
|
||||
free_mem(occupation);
|
||||
}
|
||||
|
||||
|
||||
@ -779,10 +769,10 @@ TBOX deskew_block_coords( //block box
|
||||
void compute_line_occupation( //project blobs
|
||||
TO_BLOCK *block, //block to do
|
||||
float gradient, //global skew
|
||||
int32_t min_y, //min coord in block
|
||||
int32_t max_y, //in block
|
||||
int32_t min_y, //min coord in block
|
||||
int32_t max_y, //in block
|
||||
int32_t *occupation, //output projection
|
||||
int32_t *deltas //derivative
|
||||
int32_t *deltas //derivative
|
||||
) {
|
||||
int32_t line_count; //maxy-miny+1
|
||||
int32_t line_index; //of scan line
|
||||
@ -1162,11 +1152,8 @@ void compute_row_stats( //find lines
|
||||
TO_ROW_IT row_it = block->get_rows ();
|
||||
//number of rows
|
||||
int16_t rowcount = row_it.length ();
|
||||
TO_ROW **rows; //for choose nth
|
||||
|
||||
rows = (TO_ROW **) alloc_mem (rowcount * sizeof (TO_ROW *));
|
||||
if (rows == nullptr)
|
||||
MEMORY_OUT.error ("compute_row_stats", ABORT, nullptr);
|
||||
// for choose nth
|
||||
std::vector<TO_ROW*> rows(rowcount);
|
||||
rowcount = 0;
|
||||
prev_row = nullptr;
|
||||
row_it.move_to_last (); //start at bottom
|
||||
@ -1190,13 +1177,13 @@ void compute_row_stats( //find lines
|
||||
tprintf ("Blob based spacing=(%g,%g), offset=%g",
|
||||
block->line_size, block->line_spacing, block->baseline_offset);
|
||||
if (rowcount > 0) {
|
||||
row_index = choose_nth_item (rowcount * 3 / 4, rows, rowcount,
|
||||
row_index = choose_nth_item(rowcount * 3 / 4, &rows[0], rowcount,
|
||||
sizeof (TO_ROW *), row_spacing_order);
|
||||
iqr = rows[row_index]->spacing;
|
||||
row_index = choose_nth_item (rowcount / 4, rows, rowcount,
|
||||
row_index = choose_nth_item(rowcount / 4, &rows[0], rowcount,
|
||||
sizeof (TO_ROW *), row_spacing_order);
|
||||
iqr -= rows[row_index]->spacing;
|
||||
row_index = choose_nth_item (rowcount / 2, rows, rowcount,
|
||||
row_index = choose_nth_item(rowcount / 2, &rows[0], rowcount,
|
||||
sizeof (TO_ROW *), row_spacing_order);
|
||||
block->key_row = rows[row_index];
|
||||
if (testing_on)
|
||||
@ -1232,7 +1219,6 @@ void compute_row_stats( //find lines
|
||||
if (testing_on)
|
||||
tprintf ("\nEstimate line size=%g, spacing=%g, offset=%g\n",
|
||||
block->line_size, block->line_spacing, block->baseline_offset);
|
||||
free_mem(rows);
|
||||
}
|
||||
|
||||
|
||||
@ -2070,26 +2056,25 @@ void Textord::make_spline_rows(TO_BLOCK* block, // block to do
|
||||
*/
|
||||
void make_baseline_spline(TO_ROW *row, //row to fit
|
||||
TO_BLOCK *block) {
|
||||
int32_t *xstarts; // spline boundaries
|
||||
double *coeffs; // quadratic coeffs
|
||||
int32_t segments; // no of segments
|
||||
int32_t segments; // no of segments
|
||||
|
||||
xstarts =
|
||||
(int32_t *) alloc_mem((row->blob_list()->length() + 1) * sizeof(int32_t));
|
||||
// spline boundaries
|
||||
int32_t *xstarts = new int32_t[row->blob_list()->length() + 1];
|
||||
if (segment_baseline(row, block, segments, xstarts)
|
||||
&& !textord_straight_baselines && !textord_parallel_baselines) {
|
||||
coeffs = linear_spline_baseline(row, block, segments, xstarts);
|
||||
} else {
|
||||
xstarts[1] = xstarts[segments];
|
||||
segments = 1;
|
||||
coeffs = (double *) alloc_mem (3 * sizeof (double));
|
||||
coeffs = new double[3];
|
||||
coeffs[0] = 0;
|
||||
coeffs[1] = row->line_m ();
|
||||
coeffs[2] = row->line_c ();
|
||||
}
|
||||
row->baseline = QSPLINE (segments, xstarts, coeffs);
|
||||
free_mem(coeffs);
|
||||
free_mem(xstarts);
|
||||
delete[] coeffs;
|
||||
delete[] xstarts;
|
||||
}
|
||||
|
||||
|
||||
@ -2203,22 +2188,21 @@ double *
|
||||
linear_spline_baseline ( //split baseline
|
||||
TO_ROW * row, //row to fit
|
||||
TO_BLOCK * block, //block it came from
|
||||
int32_t & segments, //no fo segments
|
||||
int32_t xstarts[] //coords of segments
|
||||
int32_t & segments, //no fo segments
|
||||
int32_t xstarts[] //coords of segments
|
||||
) {
|
||||
int blobcount; //no of blobs
|
||||
int blobindex; //current blob
|
||||
int index1, index2; //blob numbers
|
||||
int blobs_per_segment; //blobs in each
|
||||
TBOX box; //blob box
|
||||
TBOX new_box; //new_it box
|
||||
TBOX box; //blob box
|
||||
TBOX new_box; //new_it box
|
||||
//blobs
|
||||
BLOBNBOX_IT blob_it = row->blob_list ();
|
||||
BLOBNBOX_IT new_it = blob_it; //front end
|
||||
float b, c; //fitted curve
|
||||
tesseract::DetLineFit lms;
|
||||
double *coeffs; //quadratic coeffs
|
||||
int32_t segment; //current segment
|
||||
int32_t segment; //current segment
|
||||
|
||||
box = box_next_pre_chopped (&blob_it);
|
||||
xstarts[0] = box.left ();
|
||||
@ -2231,7 +2215,8 @@ int32_t xstarts[] //coords of segments
|
||||
if (segments < 1)
|
||||
segments = 1;
|
||||
blobs_per_segment = blobcount / segments;
|
||||
coeffs = (double *) alloc_mem (segments * 3 * sizeof (double));
|
||||
// quadratic coeffs
|
||||
double *coeffs = new double[segments * 3];
|
||||
if (textord_oldbl_debug)
|
||||
tprintf
|
||||
("Linear splining baseline of %d blobs at (%d,%d), into %d segments of %d blobs\n",
|
||||
|
@ -17,6 +17,7 @@
|
||||
*
|
||||
**********************************************************************/
|
||||
|
||||
#include <vector> // for std::vector
|
||||
#include "ccstruct.h"
|
||||
#include "statistc.h"
|
||||
#include "quadlsq.h"
|
||||
@ -121,7 +122,6 @@ void Textord::make_old_baselines(TO_BLOCK* block, // block to do
|
||||
**********************************************************************/
|
||||
|
||||
void Textord::correlate_lines(TO_BLOCK *block, float gradient) {
|
||||
TO_ROW **rows; //array of ptrs
|
||||
int rowcount; /*no of rows to do */
|
||||
int rowindex; /*no of row */
|
||||
// iterator
|
||||
@ -133,17 +133,18 @@ void Textord::correlate_lines(TO_BLOCK *block, float gradient) {
|
||||
block->xheight = block->line_size;
|
||||
return; /*none to do */
|
||||
}
|
||||
rows = (TO_ROW **) alloc_mem (rowcount * sizeof (TO_ROW *));
|
||||
// array of ptrs
|
||||
std::vector <TO_ROW *> rows(rowcount);
|
||||
rowindex = 0;
|
||||
for (row_it.mark_cycle_pt (); !row_it.cycled_list (); row_it.forward ())
|
||||
//make array
|
||||
rows[rowindex++] = row_it.data ();
|
||||
|
||||
/*try to fix bad lines */
|
||||
correlate_neighbours(block, rows, rowcount);
|
||||
correlate_neighbours(block, &rows[0], rowcount);
|
||||
|
||||
if (textord_really_old_xheight || textord_old_xheight) {
|
||||
block->xheight = (float) correlate_with_stats(rows, rowcount, block);
|
||||
block->xheight = (float) correlate_with_stats(&rows[0], rowcount, block);
|
||||
if (block->xheight <= 0)
|
||||
block->xheight = block->line_size * tesseract::CCStruct::kXHeightFraction;
|
||||
if (block->xheight < textord_min_xheight)
|
||||
@ -151,8 +152,6 @@ void Textord::correlate_lines(TO_BLOCK *block, float gradient) {
|
||||
} else {
|
||||
compute_block_xheight(block, gradient);
|
||||
}
|
||||
|
||||
free_mem(rows);
|
||||
}
|
||||
|
||||
|
||||
@ -334,28 +333,28 @@ void Textord::find_textlines(TO_BLOCK *block, // block row is in
|
||||
int partcount; /*no of partitions of */
|
||||
bool holed_line = false; //lost too many blobs
|
||||
int bestpart; /*biggest partition */
|
||||
char *partids; /*partition no of each blob */
|
||||
int partsizes[MAXPARTS]; /*no in each partition */
|
||||
int lineheight; /*guessed x-height */
|
||||
float jumplimit; /*allowed delta change */
|
||||
int *xcoords; /*useful sample points */
|
||||
int *ycoords; /*useful sample points */
|
||||
TBOX *blobcoords; /*edges of blob rectangles */
|
||||
int blobcount; /*no of blobs on line */
|
||||
float *ydiffs; /*diffs from 1st approx */
|
||||
int pointcount; /*no of coords */
|
||||
int xstarts[SPLINESIZE + 1]; //segment boundaries
|
||||
int segments; //no of segments
|
||||
|
||||
//no of blobs in row
|
||||
blobcount = row->blob_list ()->length ();
|
||||
partids = (char *) alloc_mem (blobcount * sizeof (char));
|
||||
xcoords = (int *) alloc_mem (blobcount * sizeof (int));
|
||||
ycoords = (int *) alloc_mem (blobcount * sizeof (int));
|
||||
blobcoords = (TBOX *) alloc_mem (blobcount * sizeof (TBOX));
|
||||
ydiffs = (float *) alloc_mem (blobcount * sizeof (float));
|
||||
// partition no of each blob
|
||||
std::vector<char> partids(blobcount);
|
||||
// useful sample points
|
||||
std::vector<int> xcoords(blobcount);
|
||||
// useful sample points
|
||||
std::vector<int> ycoords(blobcount);
|
||||
// edges of blob rectangles
|
||||
std::vector<TBOX> blobcoords(blobcount);
|
||||
// diffs from 1st approx
|
||||
std::vector<float> ydiffs(blobcount);
|
||||
|
||||
lineheight = get_blob_coords (row, (int) block->line_size, blobcoords,
|
||||
lineheight = get_blob_coords(row, (int)block->line_size, &blobcoords[0],
|
||||
holed_line, blobcount);
|
||||
/*limit for line change */
|
||||
jumplimit = lineheight * textord_oldbl_jumplimit;
|
||||
@ -368,40 +367,34 @@ void Textord::find_textlines(TO_BLOCK *block, // block row is in
|
||||
block->line_size, lineheight, jumplimit);
|
||||
}
|
||||
if (holed_line)
|
||||
make_holed_baseline (blobcoords, blobcount, spline, &row->baseline,
|
||||
make_holed_baseline(&blobcoords[0], blobcount, spline, &row->baseline,
|
||||
row->line_m ());
|
||||
else
|
||||
make_first_baseline (blobcoords, blobcount,
|
||||
xcoords, ycoords, spline, &row->baseline, jumplimit);
|
||||
make_first_baseline(&blobcoords[0], blobcount,
|
||||
&xcoords[0], &ycoords[0], spline, &row->baseline, jumplimit);
|
||||
#ifndef GRAPHICS_DISABLED
|
||||
if (textord_show_final_rows)
|
||||
row->baseline.plot (to_win, ScrollView::GOLDENROD);
|
||||
#endif
|
||||
if (blobcount > 1) {
|
||||
bestpart = partition_line (blobcoords, blobcount,
|
||||
&partcount, partids, partsizes,
|
||||
&row->baseline, jumplimit, ydiffs);
|
||||
pointcount = partition_coords (blobcoords, blobcount,
|
||||
partids, bestpart, xcoords, ycoords);
|
||||
segments = segment_spline (blobcoords, blobcount,
|
||||
xcoords, ycoords,
|
||||
degree, pointcount, xstarts);
|
||||
bestpart = partition_line(&blobcoords[0], blobcount,
|
||||
&partcount, &partids[0], partsizes,
|
||||
&row->baseline, jumplimit, &ydiffs[0]);
|
||||
pointcount = partition_coords(&blobcoords[0], blobcount,
|
||||
&partids[0], bestpart, &xcoords[0], &ycoords[0]);
|
||||
segments = segment_spline(&blobcoords[0], blobcount,
|
||||
&xcoords[0], &ycoords[0], degree, pointcount, xstarts);
|
||||
if (!holed_line) {
|
||||
do {
|
||||
row->baseline = QSPLINE (xstarts, segments,
|
||||
xcoords, ycoords, pointcount, degree);
|
||||
row->baseline = QSPLINE(xstarts, segments,
|
||||
&xcoords[0], &ycoords[0], pointcount, degree);
|
||||
}
|
||||
while (textord_oldbl_split_splines
|
||||
&& split_stepped_spline (&row->baseline, jumplimit / 2,
|
||||
xcoords, xstarts, segments));
|
||||
&xcoords[0], xstarts, segments));
|
||||
}
|
||||
find_lesser_parts(row,
|
||||
blobcoords,
|
||||
blobcount,
|
||||
partids,
|
||||
partsizes,
|
||||
partcount,
|
||||
bestpart);
|
||||
find_lesser_parts(row, &blobcoords[0], blobcount,
|
||||
&partids[0], partsizes, partcount, bestpart);
|
||||
|
||||
}
|
||||
else {
|
||||
@ -414,20 +407,15 @@ void Textord::find_textlines(TO_BLOCK *block, // block row is in
|
||||
block->block->pdblk.bounding_box ().right ());
|
||||
|
||||
if (textord_really_old_xheight) {
|
||||
old_first_xheight (row, blobcoords, lineheight,
|
||||
old_first_xheight (row, &blobcoords[0], lineheight,
|
||||
blobcount, &row->baseline, jumplimit);
|
||||
} else if (textord_old_xheight) {
|
||||
make_first_xheight (row, blobcoords, lineheight, (int) block->line_size,
|
||||
make_first_xheight (row, &blobcoords[0], lineheight, (int)block->line_size,
|
||||
blobcount, &row->baseline, jumplimit);
|
||||
} else {
|
||||
compute_row_xheight(row, block->block->classify_rotation(),
|
||||
row->line_m(), block->line_size);
|
||||
}
|
||||
free_mem(partids);
|
||||
free_mem(xcoords);
|
||||
free_mem(ycoords);
|
||||
free_mem(blobcoords);
|
||||
free_mem(ydiffs);
|
||||
}
|
||||
|
||||
} // namespace tesseract.
|
||||
|
@ -1,8 +1,8 @@
|
||||
/**********************************************************************
|
||||
* File: pithsync.cpp (Formerly pitsync2.c)
|
||||
* Description: Code to find the optimum fixed pitch segmentation of some blobs.
|
||||
* Author: Ray Smith
|
||||
* Created: Thu Nov 19 11:48:05 GMT 1992
|
||||
* Author: Ray Smith
|
||||
* Created: Thu Nov 19 11:48:05 GMT 1992
|
||||
*
|
||||
* (C) Copyright 1992, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
@ -18,7 +18,7 @@
|
||||
**********************************************************************/
|
||||
|
||||
#include <math.h>
|
||||
#include "memry.h"
|
||||
#include <vector> // for std::vector
|
||||
#include "makerow.h"
|
||||
#include "pitsync1.h"
|
||||
#include "topitch.h"
|
||||
@ -320,7 +320,6 @@ double check_pitch_sync2( //find segmentation
|
||||
TBOX this_box; //bounding box
|
||||
TBOX next_box; //box of next blob
|
||||
FPSEGPT *segpt; //segment point
|
||||
FPCUTPT *cutpts; //array of points
|
||||
double best_cost; //best path
|
||||
double mean_sum; //computes result
|
||||
FPCUTPT *best_end; //end of best path
|
||||
@ -359,14 +358,16 @@ double check_pitch_sync2( //find segmentation
|
||||
projection_scale, occupation_count, seg_list,
|
||||
start, end);
|
||||
array_origin = left_edge - pitch;
|
||||
cutpts = (FPCUTPT *) alloc_mem ((right_edge - left_edge + pitch * 2 + 1)
|
||||
* sizeof (FPCUTPT));
|
||||
// array of points
|
||||
std::vector<FPCUTPT> cutpts(right_edge - left_edge + pitch * 2 + 1);
|
||||
for (x = array_origin; x < left_edge; x++)
|
||||
//free cuts
|
||||
cutpts[x - array_origin].setup (cutpts, array_origin, projection, zero_count, pitch, x, 0);
|
||||
cutpts[x - array_origin].setup(&cutpts[0], array_origin, projection,
|
||||
zero_count, pitch, x, 0);
|
||||
for (offset = 0; offset <= pitch_error; offset++, x++)
|
||||
//not quite free
|
||||
cutpts[x - array_origin].setup (cutpts, array_origin, projection, zero_count, pitch, x, offset);
|
||||
cutpts[x - array_origin].setup(&cutpts[0], array_origin, projection,
|
||||
zero_count, pitch, x, offset);
|
||||
|
||||
this_it = *blob_it;
|
||||
best_cost = MAX_FLOAT32;
|
||||
@ -404,7 +405,7 @@ double check_pitch_sync2( //find segmentation
|
||||
faking = true;
|
||||
offset = projection->pile_count (x);
|
||||
}
|
||||
cutpts[x - array_origin].assign (cutpts, array_origin, x,
|
||||
cutpts[x - array_origin].assign (&cutpts[0], array_origin, x,
|
||||
faking, mid_cut, offset, projection,
|
||||
projection_scale, zero_count, pitch,
|
||||
pitch_error);
|
||||
@ -416,7 +417,7 @@ double check_pitch_sync2( //find segmentation
|
||||
best_count = INT16_MAX;
|
||||
while (x < right_edge + pitch) {
|
||||
offset = x < right_edge ? right_edge - x : 0;
|
||||
cutpts[x - array_origin].assign (cutpts, array_origin, x,
|
||||
cutpts[x - array_origin].assign (&cutpts[0], array_origin, x,
|
||||
false, false, offset, projection,
|
||||
projection_scale, zero_count, pitch,
|
||||
pitch_error);
|
||||
@ -473,7 +474,6 @@ double check_pitch_sync2( //find segmentation
|
||||
if (seg_it.data ()->squares () - mean_sum < 0)
|
||||
tprintf ("Impossible sqsum=%g, mean=%g, total=%d\n",
|
||||
seg_it.data ()->squares (), seg_it.data ()->sum (), best_count);
|
||||
free_mem(cutpts);
|
||||
// tprintf("blob_count=%d, pitch=%d, sync=%g, occ=%d\n",
|
||||
// blob_count,pitch,seg_it.data()->squares()-mean_sum,
|
||||
// occupation_count);
|
||||
@ -502,29 +502,27 @@ double check_pitch_sync3( //find segmentation
|
||||
int16_t start, //start of good range
|
||||
int16_t end //end of good range
|
||||
) {
|
||||
bool faking; //illegal cut pt
|
||||
bool mid_cut; //cheap cut pt.
|
||||
int16_t left_edge; //of word
|
||||
int16_t right_edge; //of word
|
||||
int16_t x; //current coord
|
||||
int16_t array_origin; //x coord of array
|
||||
int16_t offset; //dist to legal area
|
||||
int16_t projection_offset; //from scaled projection
|
||||
int16_t prev_zero; //previous zero dist
|
||||
int16_t next_zero; //next zero dist
|
||||
int16_t zero_offset; //scan window
|
||||
int16_t best_left_x = 0; //for equals
|
||||
int16_t best_right_x = 0; //right edge
|
||||
bool faking; //illegal cut pt
|
||||
bool mid_cut; //cheap cut pt.
|
||||
int16_t left_edge; //of word
|
||||
int16_t right_edge; //of word
|
||||
int16_t x; //current coord
|
||||
int16_t array_origin; //x coord of array
|
||||
int16_t offset; //dist to legal area
|
||||
int16_t projection_offset; //from scaled projection
|
||||
int16_t prev_zero; //previous zero dist
|
||||
int16_t next_zero; //next zero dist
|
||||
int16_t zero_offset; //scan window
|
||||
int16_t best_left_x = 0; //for equals
|
||||
int16_t best_right_x = 0; //right edge
|
||||
FPSEGPT *segpt; //segment point
|
||||
FPCUTPT *cutpts; //array of points
|
||||
BOOL8 *mins; //local min results
|
||||
int minindex; //next input position
|
||||
int test_index; //index to mins
|
||||
double best_cost; //best path
|
||||
double mean_sum; //computes result
|
||||
FPCUTPT *best_end; //end of best path
|
||||
int16_t best_fake; //best fake level
|
||||
int16_t best_count; //no of cuts
|
||||
int16_t best_fake; //best fake level
|
||||
int16_t best_count; //no of cuts
|
||||
FPSEGPT_IT seg_it = seg_list; //output iterator
|
||||
|
||||
end = (end - start) % pitch;
|
||||
@ -539,16 +537,19 @@ double check_pitch_sync3( //find segmentation
|
||||
for (right_edge = projection_right; projection->pile_count (right_edge) == 0
|
||||
&& right_edge > left_edge; right_edge--);
|
||||
array_origin = left_edge - pitch;
|
||||
cutpts = (FPCUTPT *) alloc_mem ((right_edge - left_edge + pitch * 2 + 1)
|
||||
* sizeof (FPCUTPT));
|
||||
mins = (BOOL8 *) alloc_mem ((pitch_error * 2 + 1) * sizeof (BOOL8));
|
||||
// array of points
|
||||
std::vector<FPCUTPT> cutpts(right_edge - left_edge + pitch * 2 + 1);
|
||||
// local min results
|
||||
std::vector<BOOL8> mins(pitch_error * 2 + 1);
|
||||
for (x = array_origin; x < left_edge; x++)
|
||||
//free cuts
|
||||
cutpts[x - array_origin].setup (cutpts, array_origin, projection, zero_count, pitch, x, 0);
|
||||
cutpts[x - array_origin].setup(&cutpts[0], array_origin, projection,
|
||||
zero_count, pitch, x, 0);
|
||||
prev_zero = left_edge - 1;
|
||||
for (offset = 0; offset <= pitch_error; offset++, x++)
|
||||
//not quite free
|
||||
cutpts[x - array_origin].setup (cutpts, array_origin, projection, zero_count, pitch, x, offset);
|
||||
cutpts[x - array_origin].setup(&cutpts[0], array_origin, projection,
|
||||
zero_count, pitch, x, offset);
|
||||
|
||||
best_cost = MAX_FLOAT32;
|
||||
best_end = nullptr;
|
||||
@ -609,12 +610,12 @@ double check_pitch_sync3( //find segmentation
|
||||
if ((start == 0 && end == 0)
|
||||
|| !textord_fast_pitch_test
|
||||
|| (x - projection_left - start) % pitch <= end)
|
||||
cutpts[x - array_origin].assign (cutpts, array_origin, x,
|
||||
cutpts[x - array_origin].assign(&cutpts[0], array_origin, x,
|
||||
faking, mid_cut, offset, projection,
|
||||
projection_scale, zero_count, pitch,
|
||||
pitch_error);
|
||||
else
|
||||
cutpts[x - array_origin].assign_cheap (cutpts, array_origin, x,
|
||||
cutpts[x - array_origin].assign_cheap(&cutpts[0], array_origin, x,
|
||||
faking, mid_cut, offset,
|
||||
projection, projection_scale,
|
||||
zero_count, pitch,
|
||||
@ -631,7 +632,7 @@ double check_pitch_sync3( //find segmentation
|
||||
best_count = INT16_MAX;
|
||||
while (x < right_edge + pitch) {
|
||||
offset = x < right_edge ? right_edge - x : 0;
|
||||
cutpts[x - array_origin].assign (cutpts, array_origin, x,
|
||||
cutpts[x - array_origin].assign(&cutpts[0], array_origin, x,
|
||||
false, false, offset, projection,
|
||||
projection_scale, zero_count, pitch,
|
||||
pitch_error);
|
||||
@ -686,7 +687,5 @@ double check_pitch_sync3( //find segmentation
|
||||
if (seg_it.data ()->squares () - mean_sum < 0)
|
||||
tprintf ("Impossible sqsum=%g, mean=%g, total=%d\n",
|
||||
seg_it.data ()->squares (), seg_it.data ()->sum (), best_count);
|
||||
free_mem(mins);
|
||||
free_mem(cutpts);
|
||||
return seg_it.data ()->squares () - mean_sum;
|
||||
}
|
||||
|
@ -18,7 +18,6 @@
|
||||
**********************************************************************/
|
||||
|
||||
#include <math.h>
|
||||
#include "memry.h"
|
||||
#include "pitsync1.h"
|
||||
|
||||
ELISTIZE (FPSEGPT) CLISTIZE (FPSEGPT_LIST)
|
||||
|
@ -1,8 +1,8 @@
|
||||
/**********************************************************************
|
||||
* File: topitch.cpp (Formerly to_pitch.c)
|
||||
* Description: Code to determine fixed pitchness and the pitch if fixed.
|
||||
* Author: Ray Smith
|
||||
* Created: Tue Aug 24 16:57:29 BST 1993
|
||||
* Author: Ray Smith
|
||||
* Created: Tue Aug 24 16:57:29 BST 1993
|
||||
*
|
||||
* (C) Copyright 1993, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
@ -17,7 +17,6 @@
|
||||
*
|
||||
**********************************************************************/
|
||||
|
||||
#include "stderr.h"
|
||||
#include "blobbox.h"
|
||||
#include "statistc.h"
|
||||
#include "drawtord.h"
|
||||
|
@ -1,8 +1,8 @@
|
||||
/**********************************************************************
|
||||
* File: tordmain.cpp (Formerly textordp.c)
|
||||
* Description: C++ top level textord code.
|
||||
* Author: Ray Smith
|
||||
* Created: Tue Jul 28 17:12:33 BST 1992
|
||||
* Author: Ray Smith
|
||||
* Created: Tue Jul 28 17:12:33 BST 1992
|
||||
*
|
||||
* (C) Copyright 1992, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
@ -21,7 +21,6 @@
|
||||
#include "config_auto.h"
|
||||
#endif
|
||||
|
||||
#include "stderr.h"
|
||||
#include "globaloc.h"
|
||||
#include "blread.h"
|
||||
#include "blobbox.h"
|
||||
@ -459,16 +458,16 @@ bool Textord::clean_noise_from_row( //remove empties
|
||||
ROW* row //row to clean
|
||||
) {
|
||||
bool testing_on;
|
||||
TBOX blob_box; //bounding box
|
||||
TBOX blob_box; //bounding box
|
||||
C_BLOB *blob; //current blob
|
||||
C_OUTLINE *outline; //current outline
|
||||
WERD *word; //current word
|
||||
int32_t blob_size; //biggest size
|
||||
int32_t trans_count = 0; //no of transitions
|
||||
int32_t trans_threshold; //noise tolerance
|
||||
int32_t dot_count; //small objects
|
||||
int32_t norm_count; //normal objects
|
||||
int32_t super_norm_count; //real char-like
|
||||
int32_t blob_size; //biggest size
|
||||
int32_t trans_count = 0; //no of transitions
|
||||
int32_t trans_threshold; //noise tolerance
|
||||
int32_t dot_count; //small objects
|
||||
int32_t norm_count; //normal objects
|
||||
int32_t super_norm_count; //real char-like
|
||||
//words of row
|
||||
WERD_IT word_it = row->word_list ();
|
||||
C_BLOB_IT blob_it; //blob iterator
|
||||
@ -559,19 +558,18 @@ bool Textord::clean_noise_from_row( //remove empties
|
||||
void Textord::clean_noise_from_words( //remove empties
|
||||
ROW *row //row to clean
|
||||
) {
|
||||
TBOX blob_box; //bounding box
|
||||
int8_t *word_dud; //was it chucked
|
||||
TBOX blob_box; //bounding box
|
||||
C_BLOB *blob; //current blob
|
||||
C_OUTLINE *outline; //current outline
|
||||
WERD *word; //current word
|
||||
int32_t blob_size; //biggest size
|
||||
int32_t trans_count; //no of transitions
|
||||
int32_t trans_threshold; //noise tolerance
|
||||
int32_t dot_count; //small objects
|
||||
int32_t norm_count; //normal objects
|
||||
int32_t dud_words; //number discarded
|
||||
int32_t ok_words; //number remaining
|
||||
int32_t word_index; //current word
|
||||
int32_t blob_size; //biggest size
|
||||
int32_t trans_count; //no of transitions
|
||||
int32_t trans_threshold; //noise tolerance
|
||||
int32_t dot_count; //small objects
|
||||
int32_t norm_count; //normal objects
|
||||
int32_t dud_words; //number discarded
|
||||
int32_t ok_words; //number remaining
|
||||
int32_t word_index; //current word
|
||||
//words of row
|
||||
WERD_IT word_it = row->word_list ();
|
||||
C_BLOB_IT blob_it; //blob iterator
|
||||
@ -580,7 +578,8 @@ void Textord::clean_noise_from_words( //remove empties
|
||||
ok_words = word_it.length ();
|
||||
if (ok_words == 0 || textord_no_rejects)
|
||||
return;
|
||||
word_dud = (int8_t *) alloc_mem (ok_words * sizeof (int8_t));
|
||||
// was it chucked
|
||||
std::vector<int8_t> word_dud(ok_words);
|
||||
dud_words = 0;
|
||||
ok_words = 0;
|
||||
word_index = 0;
|
||||
@ -664,7 +663,6 @@ void Textord::clean_noise_from_words( //remove empties
|
||||
}
|
||||
word_index++;
|
||||
}
|
||||
free_mem(word_dud);
|
||||
}
|
||||
|
||||
// Remove outlines that are a tiny fraction in either width or height
|
||||
@ -885,8 +883,6 @@ void tweak_row_baseline(ROW *row,
|
||||
int32_t blob_count; //no of blobs
|
||||
int32_t src_index; //source segment
|
||||
int32_t dest_index; //destination segment
|
||||
int32_t *xstarts; //spline segments
|
||||
double *coeffs; //spline coeffs
|
||||
float ydiff; //baseline error
|
||||
float x_centre; //centre of blob
|
||||
//words of row
|
||||
@ -901,12 +897,10 @@ void tweak_row_baseline(ROW *row,
|
||||
}
|
||||
if (blob_count == 0)
|
||||
return;
|
||||
xstarts =
|
||||
(int32_t *) alloc_mem ((blob_count + row->baseline.segments + 1) *
|
||||
sizeof (int32_t));
|
||||
coeffs =
|
||||
(double *) alloc_mem ((blob_count + row->baseline.segments) * 3 *
|
||||
sizeof (double));
|
||||
// spline segments
|
||||
std::vector<int32_t> xstarts(blob_count + row->baseline.segments + 1);
|
||||
// spline coeffs
|
||||
std::vector<double> coeffs((blob_count + row->baseline.segments) * 3);
|
||||
|
||||
src_index = 0;
|
||||
dest_index = 0;
|
||||
@ -978,7 +972,5 @@ void tweak_row_baseline(ROW *row,
|
||||
xstarts[dest_index] = row->baseline.xcoords[src_index];
|
||||
}
|
||||
//turn to spline
|
||||
row->baseline = QSPLINE (dest_index, xstarts, coeffs);
|
||||
free_mem(xstarts);
|
||||
free_mem(coeffs);
|
||||
row->baseline = QSPLINE(dest_index, &xstarts[0], &coeffs[0]);
|
||||
}
|
||||
|
@ -1,8 +1,8 @@
|
||||
/**********************************************************************
|
||||
* File: wordseg.cpp (Formerly wspace.c)
|
||||
* Description: Code to segment the blobs into words.
|
||||
* Author: Ray Smith
|
||||
* Created: Fri Oct 16 11:32:28 BST 1992
|
||||
* Author: Ray Smith
|
||||
* Created: Fri Oct 16 11:32:28 BST 1992
|
||||
*
|
||||
* (C) Copyright 1992, Hewlett-Packard Ltd.
|
||||
** Licensed under the Apache License, Version 2.0 (the "License");
|
||||
@ -17,7 +17,6 @@
|
||||
*
|
||||
**********************************************************************/
|
||||
|
||||
#include "stderr.h"
|
||||
#include "blobbox.h"
|
||||
#include "statistc.h"
|
||||
#include "drawtord.h"
|
||||
|
Loading…
Reference in New Issue
Block a user