Annotation of parser3/src/main/pa_dictionary.C, revision 1.22
1.1 parser 1: /** @file
2: Parser: dictionary class impl.
3:
1.22 ! paf 4: Copyright (c) 2001-2004 ArtLebedev Group (http://www.artlebedev.com)
1.12 paf 5: Author: Alexandr Petrosian <paf@design.ru> (http://paf.design.ru)
1.15 paf 6: */
1.1 parser 7:
1.22 ! paf 8: static const char * const IDENT_DICTIONARY_C="$Date: 2003/11/20 17:46:02 $";
1.1 parser 9:
10: #include "pa_dictionary.h"
1.4 parser 11: #include "pa_exception.h"
1.1 parser 12:
1.18 paf 13: // could not make this static: gcc complains "prev decl was extern"
14: void pa_dictionary_add_first(Table::element_type row, Dictionary* self) {
1.4 parser 15: // get a=>b values
1.18 paf 16: const String* a=row->get(0);
1.4 parser 17: // empty 'a' check
1.18 paf 18: if(a->is_empty()) {
1.14 paf 19: throw Exception("parser.runtime",
1.18 paf 20: 0, //&a,
1.4 parser 21: "dictionary table 'from' column elements must not be empty");
22: }
1.19 paf 23: const String* b;
24: if(row->count()>1) { // are there any b?
25: b=row->get(1);
26: if(b->is_empty())
27: b=0;
28: } else
29: b=0;
30:
31: // record simplier 'a' for quick comparisons in 'starts' extremely-tight-callback
32: self->substs+=Dictionary::Subst(a->cstr(), b);
33:
1.18 paf 34: unsigned char c=(unsigned char)a->first_char();
35: if(!self->starting_line_of[c])
36: self->starting_line_of[c]=self->constructor_line;
1.4 parser 37:
1.18 paf 38: self->constructor_line++;
1.1 parser 39: }
1.19 paf 40: Dictionary::Dictionary(Table& atable): substs(atable.count()) {
1.4 parser 41: // clear starting_lines
42: memset(starting_line_of, 0, sizeof(starting_line_of));
1.1 parser 43: // grab first letters of first column of a table
1.19 paf 44: constructor_line=1; atable.for_each(pa_dictionary_add_first, this);
1.1 parser 45: }
46:
1.4 parser 47: #ifndef DOXYGEN
1.18 paf 48: struct First_that_begins_info {
1.4 parser 49: int line;
1.18 paf 50: const char* str;
1.4 parser 51: };
52: #endif
1.19 paf 53: static bool starts(Dictionary::Subst subst, First_that_begins_info* info) {
1.4 parser 54: // skip irrelevant lines
1.18 paf 55: if(info->line>1) {
56: --info->line;
1.4 parser 57: return 0;
58: }
1.1 parser 59:
1.19 paf 60: return strncmp(subst.from, info->str, subst.from_length)==0;
1.1 parser 61: }
1.19 paf 62: Dictionary::Subst Dictionary::first_that_begins(const char* str) const {
1.18 paf 63: First_that_begins_info info;
1.21 paf 64: if((info.line=starting_line_of[(unsigned char)*str])) {
1.18 paf 65: info.str=str;
1.19 paf 66: return substs.first_that(starts, &info);
1.4 parser 67: } else
1.19 paf 68: return 0;
1.1 parser 69: }
E-mail: