forked from GitHub/gf-core
partial support for epsilon rules
This commit is contained in:
@@ -211,11 +211,13 @@ struct PGF_INTERNAL_DECL PgfSymbolALLCAPIT {
|
|||||||
|
|
||||||
struct PGF_INTERNAL_DECL PgfConcrLincat;
|
struct PGF_INTERNAL_DECL PgfConcrLincat;
|
||||||
struct PGF_INTERNAL_DECL PgfLincatBackref;
|
struct PGF_INTERNAL_DECL PgfLincatBackref;
|
||||||
|
struct PGF_INTERNAL_DECL PgfLincatEpsilon;
|
||||||
|
|
||||||
struct PGF_INTERNAL_DECL PgfLincatField {
|
struct PGF_INTERNAL_DECL PgfLincatField {
|
||||||
ref<PgfConcrLincat> lincat;
|
ref<PgfConcrLincat> lincat;
|
||||||
ref<PgfText> name;
|
ref<PgfText> name;
|
||||||
ref<Vector<PgfLincatBackref>> backrefs;
|
ref<Vector<PgfLincatBackref>> backrefs;
|
||||||
|
ref<Vector<PgfLincatEpsilon>> epsilons;
|
||||||
|
|
||||||
static void release(ref<PgfLincatField> field);
|
static void release(ref<PgfLincatField> field);
|
||||||
};
|
};
|
||||||
@@ -257,6 +259,11 @@ struct PGF_INTERNAL_DECL PgfLincatBackref {
|
|||||||
size_t dot;
|
size_t dot;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
struct PGF_INTERNAL_DECL PgfLincatEpsilon {
|
||||||
|
ref<PgfConcrLin> lin;
|
||||||
|
size_t seq_index;
|
||||||
|
};
|
||||||
|
|
||||||
struct PGF_INTERNAL_DECL PgfConcrPrintname {
|
struct PGF_INTERNAL_DECL PgfConcrPrintname {
|
||||||
ref<PgfText> printname;
|
ref<PgfText> printname;
|
||||||
PgfText name;
|
PgfText name;
|
||||||
|
|||||||
@@ -137,6 +137,19 @@ public:
|
|||||||
this->args[d] = choice;
|
this->args[d] = choice;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
ParseItem(ParseItemConts *conts, PgfLincatEpsilon *epsilon, prob_t outside_prob)
|
||||||
|
{
|
||||||
|
this->outside_prob = outside_prob;
|
||||||
|
this->inside_prob = epsilon->lin->absfun->prob;
|
||||||
|
this->conts = conts;
|
||||||
|
this->lin = epsilon->lin;
|
||||||
|
this->seq_index = epsilon->seq_index;
|
||||||
|
this->dot = 0;
|
||||||
|
|
||||||
|
size_t n_args = epsilon->lin->absfun->type->hypos->len;
|
||||||
|
memset(this->args, 0, sizeof(Choice*)*n_args);
|
||||||
|
}
|
||||||
|
|
||||||
ParseItem(ParseItem *item,
|
ParseItem(ParseItem *item,
|
||||||
size_t d, Choice *choice)
|
size_t d, Choice *choice)
|
||||||
{
|
{
|
||||||
@@ -152,20 +165,33 @@ public:
|
|||||||
this->args[d] = choice;
|
this->args[d] = choice;
|
||||||
}
|
}
|
||||||
|
|
||||||
static void bu_predict(PgfLincatBackref *backref, State *state, Choice *choice)
|
static void bu_predict(ref<PgfLincatField> field, State *state, Choice *choice)
|
||||||
{
|
{
|
||||||
ref<PgfSequence> seq =
|
for (size_t i = 0; i < field->backrefs->len; i++) {
|
||||||
*vector_elem(backref->lin->seqs, backref->seq_index);
|
ref<PgfLincatBackref> backref = vector_elem(field->backrefs, i);
|
||||||
PgfSymbol sym = seq->syms.data[backref->dot];
|
|
||||||
ref<PgfSymbolCat> symcat = ref<PgfSymbolCat>::untagged(sym);
|
|
||||||
|
|
||||||
size_t index = backref->seq_index % backref->lin->lincat->fields->len;
|
ref<PgfSequence> seq =
|
||||||
ref<PgfLincatField> field = vector_elem(backref->lin->lincat->fields, index);
|
*vector_elem(backref->lin->seqs, backref->seq_index);
|
||||||
ParseItemConts *conts = choice->conts->state->get_conts(field, 0);
|
PgfSymbol sym = seq->syms.data[backref->dot];
|
||||||
|
ref<PgfSymbolCat> symcat = ref<PgfSymbolCat>::untagged(sym);
|
||||||
|
|
||||||
size_t n_args = backref->lin->absfun->type->hypos->len;
|
size_t index = backref->seq_index % backref->lin->lincat->fields->len;
|
||||||
state->queue.push(new(n_args) ParseItem(conts, backref,
|
ref<PgfLincatField> up_field = vector_elem(backref->lin->lincat->fields, index);
|
||||||
symcat->d, choice));
|
ParseItemConts *conts = choice->conts->state->get_conts(up_field, 0);
|
||||||
|
|
||||||
|
size_t n_args = backref->lin->absfun->type->hypos->len;
|
||||||
|
state->queue.push(new(n_args) ParseItem(conts, backref,
|
||||||
|
symcat->d, choice));
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
static void eps_predict(ref<PgfLincatField> field, State *state, ParseItemConts *conts, prob_t outside_prob)
|
||||||
|
{
|
||||||
|
for (size_t i = 0; i < field->epsilons->len; i++) {
|
||||||
|
ref<PgfLincatEpsilon> epsilon = vector_elem(field->epsilons, i);
|
||||||
|
size_t n_args = epsilon->lin->absfun->type->hypos->len;
|
||||||
|
state->queue.push(new(n_args) ParseItem(conts, epsilon, outside_prob));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
void combine(State *state, Choice *choice)
|
void combine(State *state, Choice *choice)
|
||||||
@@ -229,10 +255,7 @@ public:
|
|||||||
for (ParseItem *item : conts->items) {
|
for (ParseItem *item : conts->items) {
|
||||||
item->combine(parser->after,choice);
|
item->combine(parser->after,choice);
|
||||||
}
|
}
|
||||||
for (size_t i = 0; i < conts->field->backrefs->len; i++) {
|
bu_predict(conts->field,parser->after,choice);
|
||||||
ref<PgfLincatBackref> backref = vector_elem(conts->field->backrefs, i);
|
|
||||||
bu_predict(backref,parser->after,choice);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -254,6 +277,8 @@ public:
|
|||||||
|
|
||||||
ParseItemConts *conts = parser->after->get_conts(field, 0);
|
ParseItemConts *conts = parser->after->get_conts(field, 0);
|
||||||
conts->items.push_back(this);
|
conts->items.push_back(this);
|
||||||
|
|
||||||
|
eps_predict(field, parser->after, conts, inside_prob+outside_prob);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
default:;
|
default:;
|
||||||
|
|||||||
@@ -1506,6 +1506,7 @@ public:
|
|||||||
vector_elem(db_fields, i)->lincat = lincat;
|
vector_elem(db_fields, i)->lincat = lincat;
|
||||||
vector_elem(db_fields, i)->name = name;
|
vector_elem(db_fields, i)->name = name;
|
||||||
vector_elem(db_fields, i)->backrefs = 0;
|
vector_elem(db_fields, i)->backrefs = 0;
|
||||||
|
vector_elem(db_fields, i)->epsilons = 0;
|
||||||
}
|
}
|
||||||
lincat->fields = db_fields;
|
lincat->fields = db_fields;
|
||||||
|
|
||||||
|
|||||||
@@ -684,6 +684,7 @@ ref<Vector<PgfLincatField>> PgfReader::read_lincat_fields(ref<PgfConcrLincat> li
|
|||||||
field->lincat = lincat;
|
field->lincat = lincat;
|
||||||
field->name = read_text();
|
field->name = read_text();
|
||||||
field->backrefs = 0;
|
field->backrefs = 0;
|
||||||
|
field->epsilons = 0;
|
||||||
}
|
}
|
||||||
return fields;
|
return fields;
|
||||||
}
|
}
|
||||||
@@ -717,7 +718,19 @@ ref<PgfConcrLin> PgfReader::read_lin()
|
|||||||
ref<PgfPResult> result = *vector_elem(lin->res, seq_index / n_fields);
|
ref<PgfPResult> result = *vector_elem(lin->res, seq_index / n_fields);
|
||||||
|
|
||||||
size_t dot = 0;
|
size_t dot = 0;
|
||||||
if (dot < seq->syms.len) {
|
if (dot >= seq->syms.len) {
|
||||||
|
size_t index = seq_index % n_fields;
|
||||||
|
ref<Vector<PgfLincatEpsilon>> epsilons =
|
||||||
|
vector_elem(lin->lincat->fields,index)->epsilons;
|
||||||
|
epsilons =
|
||||||
|
vector_resize(epsilons, epsilons->len+1,
|
||||||
|
PgfDB::get_txn_id());
|
||||||
|
vector_elem(lin->lincat->fields,index)->epsilons = epsilons;
|
||||||
|
ref<PgfLincatEpsilon> epsilon =
|
||||||
|
vector_elem(epsilons,epsilons->len-1);
|
||||||
|
epsilon->lin = lin;
|
||||||
|
epsilon->seq_index = seq_index;
|
||||||
|
} else {
|
||||||
PgfSymbol sym = *vector_elem(&seq->syms,dot);
|
PgfSymbol sym = *vector_elem(&seq->syms,dot);
|
||||||
switch (ref<PgfSymbol>::get_tag(sym)) {
|
switch (ref<PgfSymbol>::get_tag(sym)) {
|
||||||
case PgfSymbolCat::tag: {
|
case PgfSymbolCat::tag: {
|
||||||
|
|||||||
Reference in New Issue
Block a user