56 static const int kMaxNumChunks = 64;
76 while (srcpt != start);
85 for (outline = srcline; outline != NULL; outline = outline->
next) {
104 if (srcpt->
flags[1] == 2)
108 while (srcpt != start);
116 while (srcpt != real_start);
125 for (outline = srcline; outline != NULL; outline = outline->
next) {
133 static SEAM* CheckSeam(
int debug_level,
inT32 blob_number,
TWERD* word,
136 if (seam == NULL || blob->
outlines == NULL || other_blob->
outlines == NULL ||
146 #ifndef GRAPHICS_DISABLED 150 tprintf(
"\n** seam being removed ** \n");
182 seam =
new SEAM(0.0f, location);
189 seam->
Print(
"Good seam picked=");
191 tprintf(
"\n** no seam picked *** \n");
194 seam->
ApplySeam(italic_blob, blob, other_blob);
197 seam = CheckSeam(
chop_debug, blob_number, word, blob, other_blob,
208 seam =
new SEAM(0.0f, location);
209 seam->
ApplySeam(italic_blob, blob, other_blob);
210 seam = CheckSeam(
chop_debug, blob_number, word, blob, other_blob,
232 bool italic_blob,
WERD_RES *word_res,
235 for (*blob_number = 0; *blob_number < word->
NumBlobs(); ++*blob_number) {
243 TPOINT original_topleft, original_botright;
247 TBOX original_box =
TBOX(original_topleft.
x, original_botright.
y,
248 original_botright.
x, original_topleft.
y);
250 bool almost_equal_box =
false;
252 for (
int i = 0; i < boxes.
size(); i++) {
256 almost_equal_box =
true;
261 (!almost_equal_box && num_overlap > 1)) {
285 length = seams.
size();
286 for (index = 0; index < length; index++)
301 for (outline = blob->
outlines; outline != NULL; outline = outline->
next) {
302 edgept = outline->
loop;
306 edgept = edgept->
next;
308 while (edgept != outline->
loop);
331 bool split_next_to_fragment,
340 bool split_point_from_dict = (*blob_number != -1);
341 if (split_point_from_dict) {
345 split_next_to_fragment);
348 if (*blob_number == -1)
356 if (blob_choices[*blob_number] == NULL)
358 if (!split_point_from_dict) {
360 rating_ceiling = blob_choices[*blob_number]->rating();
400 for (
int b = 0; b < num_blobs; ++b) {
411 BLOB_CHOICE_LIST* choices = word->
ratings->
get(col, row);
412 if (choices != NULL) {
413 BLOB_CHOICE_IT bc_it(choices);
414 for (bc_it.mark_cycle_pt(); !bc_it.cycled_list(); bc_it.forward()) {
415 bc_it.data()->set_matrix_cell(col, row);
438 if (word->
blamer_bundle != NULL && this->fill_lattice_ != NULL) {
443 tprintf(
"Final Ratings Matrix:\n");
468 for (
int i = 0; i < num_blobs; ++i) {
469 BLOB_CHOICE_LIST* choices = word->
ratings->
get(i, i);
470 if (choices == NULL || choices->empty()) {
473 BLOB_CHOICE_IT bc_it(choices);
478 false,
false, word, &blob_number);
479 if (seam == NULL)
break;
499 pain_points, blamer_bundle);
500 pain_point.
col = blob_number + 1;
501 pain_point.
row = blob_number + 1;
503 pain_points, blamer_bundle);
512 word, pain_points, best_choice_bundle, blamer_bundle);
542 float rating_ceiling,
bool split_next_to_fragment) {
546 int worst_index = -1;
548 int worst_index_near_fragment = -1;
553 tprintf(
"rating_ceiling = %8.4f\n", rating_ceiling);
555 tprintf(
"rating_ceiling = No Limit\n");
558 if (split_next_to_fragment && blob_choices.
size() > 0) {
560 if (blob_choices[0] != NULL) {
562 blob_choices[0]->unichar_id());
568 for (x = 0; x < blob_choices.
size(); ++x) {
569 if (blob_choices[x] == NULL) {
573 blob_choice = blob_choices[x];
575 if (split_next_to_fragment && x+1 < blob_choices.
size()) {
576 if (blob_choices[x + 1] != NULL) {
578 blob_choices[x + 1]->unichar_id());
580 fragments[x + 1] = NULL;
583 if (blob_choice->
rating() < rating_ceiling &&
586 if (blob_choice->
rating() > worst) {
588 worst = blob_choice->
rating();
590 if (split_next_to_fragment) {
592 bool expand_following_fragment =
593 (x + 1 < blob_choices.
size() &&
594 fragments[x+1] != NULL && !fragments[x+1]->
is_beginning());
595 bool expand_preceding_fragment =
596 (x > 0 && fragments[x-1] != NULL && !fragments[x-1]->
is_ending());
597 if ((expand_following_fragment || expand_preceding_fragment) &&
598 blob_choice->
rating() > worst_near_fragment) {
599 worst_index_near_fragment = x;
600 worst_near_fragment = blob_choice->
rating();
602 tprintf(
"worst_index_near_fragment=%d" 603 " expand_following_fragment=%d" 604 " expand_preceding_fragment=%d\n",
605 worst_index_near_fragment,
606 expand_following_fragment,
607 expand_preceding_fragment);
617 return worst_index_near_fragment != -1 ?
618 worst_index_near_fragment : worst_index;
631 for (
int i = 0; i < fixpt->
size(); i++) {
632 if ((*fixpt)[i].begin + 1 == (*fixpt)[i].end &&
633 (*fixpt)[i].dangerous &&
634 (*fixpt)[i].correct_is_ngram) {
635 return (*fixpt)[i].begin;
void remove_edgept(EDGEPT *point)
int check_blob(TBLOB *blob)
void UndoSeam(TBLOB *blob, TBLOB *other_blob) const
EDGEPT * restore_outline(EDGEPT *start)
void RemapForSplit(int index)
Bundle together all the things pertaining to the best choice/state.
void InsertSeam(int blob_number, SEAM *seam)
virtual BLOB_CHOICE_LIST * classify_piece(const GenericVector< SEAM *> &seams, inT16 start, inT16 end, const char *description, TWERD *word, BlamerBundle *blamer_bundle)
SEAM * chop_overlapping_blob(const GenericVector< TBOX > &boxes, bool italic_blob, WERD_RES *word_res, int *blob_number)
GenericVector< TBLOB * > blobs
SEAM * improve_one_blob(const GenericVector< BLOB_CHOICE *> &blob_choices, DANGERR *fixpt, bool split_next_to_fragment, bool italic_blob, WERD_RES *word, int *blob_number)
bool AcceptableChoiceFound()
Struct to store information maintained by various language model components.
void insert(T t, int index)
bool SharesPosition(const SEAM &other) const
int wordrec_max_join_chunks
SEAM * attempt_blob_chop(TWERD *word, TBLOB *blob, inT32 blob_number, bool italic_blob, const GenericVector< SEAM *> &seams)
const UNICHARSET & getUnicharset() const
bool almost_equal(const TBOX &box, int tolerance) const
void DenormTransform(const DENORM *last_denorm, const TPOINT &pt, TPOINT *original) const
void BlameClassifierOrLangModel(const WERD_RES *word, const UNICHARSET &unicharset, bool valid_permuter, bool debug)
PointerVector< LanguageModelState > beam
WERD_CHOICE * best_choice
TBOX bounding_box() const
SEAM * chop_numbered_blob(TWERD *word, inT32 blob_number, bool italic_blob, const GenericVector< SEAM *> &seams)
int any_shared_split_points(const GenericVector< SEAM *> &seams, SEAM *seam)
GenericVector< SEAM * > seam_array
bool ChoiceIsCorrect(const WERD_CHOICE *word_choice) const
void reset_hyphen_vars(bool last_word_on_line)
IncorrectResultReason incorrect_result_reason() const
void chop_word_main(WERD_RES *word)
bool contains(const FCOORD pt) const
BOOL8 flag(WERD_FLAGS mask) const
int select_blob_to_split(const GenericVector< BLOB_CHOICE *> &blob_choices, float rating_ceiling, bool split_next_to_fragment)
void restore_outline_tree(TESSLINE *srcline)
void put(ICOORD pos, const T &thing)
int repair_unchopped_blobs
void UpdateSegSearchNodes(float rating_cert_scale, int starting_col, GenericVector< SegSearchPending > *pending, WERD_RES *word_res, LMPainPoints *pain_points, BestChoiceBundle *best_choice_bundle, BlamerBundle *blamer_bundle)
double overlap_fraction(const TBOX &box) const
DANGERR fixpt
Places to try to fix the word suggested by ambiguity checking.
BlamerBundle * blamer_bundle
inT16 total_containment(TBLOB *blob1, TBLOB *blob2)
bool ContainedByBlob(const TBLOB &blob) const
void ResetNGramSearch(WERD_RES *word_res, BestChoiceBundle *best_choice_bundle, GenericVector< SegSearchPending > *pending)
static bool valid_word_permuter(uinT8 perm, bool numbers_ok)
Check all the DAWGs to see if this word is in any of them.
WERD_CHOICE_LIST best_choices
bool PrepareToInsertSeam(const GenericVector< SEAM *> &seams, const GenericVector< TBLOB *> &blobs, int insert_index, bool modify)
void display_blob(TBLOB *blob, C_COL color)
bool divisible_blob(TBLOB *blob, bool italic_blob, TPOINT *location)
LanguageModel * language_model_
bool wordrec_debug_blamer
bool language_model_ngram_on
const UNICHARSET * uch_set
void SegSearch(WERD_RES *word_res, BestChoiceBundle *best_choice_bundle, BlamerBundle *blamer_bundle)
void CallFillLattice(const MATRIX &ratings, const WERD_CHOICE_LIST &best_choices, const UNICHARSET &unicharset, BlamerBundle *blamer_bundle)
void FilterWordChoices(int debug_level)
void ApplySeam(bool italic_blob, TBLOB *blob, TBLOB *other_blob) const
double tessedit_certainty_threshold
bool is_beginning() const
void preserve_outline(EDGEPT *start)
void improve_by_chopping(float rating_cert_scale, WERD_RES *word, BestChoiceBundle *best_choice_bundle, BlamerBundle *blamer_bundle, LMPainPoints *pain_points, GenericVector< SegSearchPending > *pending)
void preserve_outline_tree(TESSLINE *srcline)
void print(const UNICHARSET &unicharset) const
bool has_hyphen_end(UNICHAR_ID unichar_id, bool first_pos) const
Check whether the word has a hyphen at the end.
SEAM * chop_one_blob(const GenericVector< TBOX > &boxes, const GenericVector< BLOB_CHOICE *> &blob_choices, WERD_RES *word_res, int *blob_number)
void FakeWordFromRatings(PermuterType permuter)
SEAM * pick_good_seam(TBLOB *blob)
const CHAR_FRAGMENT * get_fragment(UNICHAR_ID unichar_id) const
static TBLOB * ShallowCopy(const TBLOB &src)
int select_blob_to_split_from_fixpt(DANGERR *fixpt)
void Print(const char *label) const
void ProcessSegSearchPainPoint(float pain_point_priority, const MATRIX_COORD &pain_point, const char *pain_point_type, GenericVector< SegSearchPending > *pending, WERD_RES *word_res, LMPainPoints *pain_points, BlamerBundle *blamer_bundle)