Exemplo n.º 1
0
/**
 * This uses link_array.  It post-processes
 * this linkage, and prints the appropriate thing.  There are no fat
 * links in it.
 */
Linkage_info analyze_thin_linkage(Sentence sent, Parse_Options opts, int analyze_pass)
{
	int i;
	Linkage_info li;
	PP_node * pp;
	Postprocessor * postprocessor;
	Sublinkage *sublinkage;
	Parse_info pi = sent->parse_info;

	build_digraph(pi, word_links);
	memset(&li, 0, sizeof(li));

	sublinkage = x_create_sublinkage(pi);
	postprocessor = sent->dict->postprocessor;

	compute_link_names(sent);
	for (i=0; i<pi->N_links; i++) {
	  copy_full_link(&(sublinkage->link[i]), &(pi->link_array[i]));
	}

	if (analyze_pass==PP_FIRST_PASS) {
		post_process_scan_linkage(postprocessor, opts, sent, sublinkage);
		free_sublinkage(sublinkage);
		free_digraph(pi, word_links);
		return li;
	}

	/* The code below can be used to generate the "islands" array. For this to work,
	 * however, you have to call "build_digraph" first (as in analyze_fat_linkage).
	 * and then "free_digraph". For some reason this causes a space leak. */

	pp = post_process(postprocessor, opts, sent, sublinkage, TRUE);

	li.N_violations = 0;
	li.and_cost = 0;
	li.unused_word_cost = unused_word_cost(sent->parse_info);
	li.improper_fat_linkage = FALSE;
	li.inconsistent_domains = FALSE;
	li.disjunct_cost = disjunct_cost(pi);
	li.null_cost = null_cost(pi);
	li.link_cost = link_cost(pi);
	li.andlist = NULL;

	if (pp==NULL) {
		if (postprocessor != NULL) li.N_violations = 1;
	} else if (pp->violation!=NULL) {
		li.N_violations++;
	}

	free_sublinkage(sublinkage);
	free_digraph(pi, word_links);
	return li;
}
Exemplo n.º 2
0
static int algorithm_dispatcher(lua_State* L)
{
  // Create the back index table. It will be at index BACKINDEX_STORAGE_INDEX
  lua_createtable(L, 0, MIN_HASH_SIZE_FIX);
  
  // The actual function is stored in an upvalue.
  pgfgd_SyntacticDigraph* digraph = (pgfgd_SyntacticDigraph*) calloc(1, sizeof(pgfgd_SyntacticDigraph));
  
  construct_digraph(L, digraph);
  
  pgfgd_algorithm_fun fun = lua_touserdata(L, lua_upvalueindex(FUNCTION_UPVALUE));
  fun(digraph, lua_touserdata(L, lua_upvalueindex(USER_UPVALUE)));

  sync_digraph(L, digraph);
  
  free_digraph(digraph);

  return 0;
}
Exemplo n.º 3
0
/**
 * This procedure mimics analyze_fat_linkage in order to
 * extract the sublinkages and copy them to the Linkage
 * data structure passed in.
 */
void extract_fat_linkage(Sentence sent, Parse_Options opts, Linkage linkage)
{
	int i, j, N_thin_links;
	DIS_node *d_root;
	int num_sublinkages;
	Sublinkage * sublinkage;
	Parse_info pi = sent->parse_info;

	sublinkage = x_create_sublinkage(pi);
	build_digraph(pi, word_links);
	structure_violation = FALSE;
	d_root = build_DIS_CON_tree(pi, word_links);

	if (structure_violation) {
		compute_link_names(sent);
		for (i=0; i<pi->N_links; i++) {
			copy_full_link(&sublinkage->link[i],&(pi->link_array[i]));
		}

		linkage->num_sublinkages=1;
		linkage->sublinkage = ex_create_sublinkage(pi);

		/* This will have fat links! */
		for (i=0; i<pi->N_links; ++i) {
			linkage->sublinkage->link[i] = excopy_link(sublinkage->link[i]);
		}

		free_sublinkage(sublinkage);
		free_digraph(pi, word_links);
		free_DIS_tree(d_root);
		return;
	}

	/* first get number of sublinkages and allocate space */
	num_sublinkages = 0;
	for (;;) {
		num_sublinkages++;
		if (!advance_DIS(d_root)) break;
	}

	linkage->num_sublinkages = num_sublinkages;
	linkage->sublinkage =
		(Sublinkage *) exalloc(sizeof(Sublinkage)*num_sublinkages);
	for (i=0; i<num_sublinkages; ++i) {
		linkage->sublinkage[i].link = NULL;
		linkage->sublinkage[i].pp_info = NULL;
		linkage->sublinkage[i].violation = NULL;
	}

	/* now fill out the sublinkage arrays */
	compute_link_names(sent);

	num_sublinkages = 0;
	for (;;) {
		for (i=0; i<pi->N_links; i++) {
			patch_array[i].used = patch_array[i].changed = FALSE;
			patch_array[i].newl = pi->link_array[i].l;
			patch_array[i].newr = pi->link_array[i].r;
			copy_full_link(&sublinkage->link[i], &(pi->link_array[i]));
		}
		fill_patch_array_DIS(d_root, NULL, word_links);

		for (i=0; i<pi->N_links; i++) {
			if (patch_array[i].changed || patch_array[i].used) {
				sublinkage->link[i]->l = patch_array[i].newl;
				sublinkage->link[i]->r = patch_array[i].newr;
			} else if ((dfs_root_word[pi->link_array[i].l] != -1) &&
					   (dfs_root_word[pi->link_array[i].r] != -1)) {
				sublinkage->link[i]->l = -1;
			}
		}

		compute_pp_link_array_connectors(sent, sublinkage);
		compute_pp_link_names(sent, sublinkage);

		/* Don't copy the fat links into the linkage */
		N_thin_links = 0;
		for (i= 0; i<pi->N_links; ++i) {
			if (sublinkage->link[i]->l == -1) continue;
			N_thin_links++;
		}

		linkage->sublinkage[num_sublinkages].num_links = N_thin_links;
		linkage->sublinkage[num_sublinkages].link =
			(Link *) exalloc(sizeof(Link)*N_thin_links);
		linkage->sublinkage[num_sublinkages].pp_info = NULL;
		linkage->sublinkage[num_sublinkages].violation = NULL;

		for (i=0, j=0; i<pi->N_links; ++i) {
			if (sublinkage->link[i]->l == -1) continue;
			linkage->sublinkage[num_sublinkages].link[j++] =
				excopy_link(sublinkage->link[i]);
		}


		num_sublinkages++;
		if (!advance_DIS(d_root)) break;
	}

	free_sublinkage(sublinkage);
	free_digraph(pi, word_links);
	free_DIS_tree(d_root);
}
Exemplo n.º 4
0
/**
 * This uses link_array.  It enumerates and post-processes
 * all the linkages represented by this one.  We know this contains
 * at least one fat link.
 */
Linkage_info analyze_fat_linkage(Sentence sent, Parse_Options opts, int analyze_pass)
{
	int i;
	Linkage_info li;
	DIS_node *d_root;
	PP_node *pp;
	Postprocessor *postprocessor;
	Sublinkage *sublinkage;
	Parse_info pi = sent->parse_info;
	PP_node accum;			   /* for domain ancestry check */
	D_type_list * dtl0, * dtl1;  /* for domain ancestry check */

	sublinkage = x_create_sublinkage(pi);
	postprocessor = sent->dict->postprocessor;
	build_digraph(pi, word_links);
	structure_violation = FALSE;
	d_root = build_DIS_CON_tree(pi, word_links); /* may set structure_violation to TRUE */

	li.N_violations = 0;
	li.improper_fat_linkage = structure_violation;
	li.inconsistent_domains = FALSE;
	li.unused_word_cost = unused_word_cost(sent->parse_info);
	li.disjunct_cost = disjunct_cost(pi);
	li.null_cost = null_cost(pi);
	li.link_cost = link_cost(pi);
	li.and_cost = 0;
	li.andlist = NULL;

	if (structure_violation) {
		li.N_violations++;
		free_sublinkage(sublinkage);
		free_digraph(pi, word_links);
		free_DIS_tree(d_root);
		return li;
	}

	if (analyze_pass==PP_SECOND_PASS) {
	  li.andlist = build_andlist(sent, word_links);
	  li.and_cost = li.andlist->cost;
	}
	else li.and_cost = 0;

	compute_link_names(sent);

	for (i=0; i<pi->N_links; i++) accum.d_type_array[i] = NULL;

	for (;;) {		/* loop through all the sub linkages */
		for (i=0; i<pi->N_links; i++) {
			patch_array[i].used = patch_array[i].changed = FALSE;
			patch_array[i].newl = pi->link_array[i].l;
			patch_array[i].newr = pi->link_array[i].r;
			copy_full_link(&sublinkage->link[i], &(pi->link_array[i]));
		}
		fill_patch_array_DIS(d_root, NULL, word_links);

		for (i=0; i<pi->N_links; i++) {
			if (patch_array[i].changed || patch_array[i].used) {
				sublinkage->link[i]->l = patch_array[i].newl;
				sublinkage->link[i]->r = patch_array[i].newr;
			}
			else if ((dfs_root_word[pi->link_array[i].l] != -1) &&
					 (dfs_root_word[pi->link_array[i].r] != -1)) {
				sublinkage->link[i]->l = -1;
			}
		}

		compute_pp_link_array_connectors(sent, sublinkage);
		compute_pp_link_names(sent, sublinkage);

		/* 'analyze_pass' logic added ALB 1/97 */
		if (analyze_pass==PP_FIRST_PASS) {
			post_process_scan_linkage(postprocessor,opts,sent,sublinkage);
			if (!advance_DIS(d_root)) break;
			else continue;
		}

		pp = post_process(postprocessor, opts, sent, sublinkage, TRUE);

		if (pp==NULL) {
			if (postprocessor != NULL) li.N_violations = 1;
		}
		else if (pp->violation == NULL)  {
			/* the purpose of this stuff is to make sure the domain
			   ancestry for a link in each of its sentences is consistent. */

			for (i=0; i<pi->N_links; i++) {
				if (sublinkage->link[i]->l == -1) continue;
				if (accum.d_type_array[i] == NULL) {
					accum.d_type_array[i] = copy_d_type(pp->d_type_array[i]);
				} else {
					dtl0 = pp->d_type_array[i];
					dtl1 = accum.d_type_array[i];
					while((dtl0 != NULL) && (dtl1 != NULL) && (dtl0->type == dtl1->type)) {
						dtl0 = dtl0->next;
						dtl1 = dtl1->next;
					}
					if ((dtl0 != NULL) || (dtl1 != NULL)) break;
				}
			}
			if (i != pi->N_links) {
				li.N_violations++;
				li.inconsistent_domains = TRUE;
			}
		}
		else if (pp->violation!=NULL) {
			li.N_violations++;
		}

		if (!advance_DIS(d_root)) break;
	}

	for (i=0; i<pi->N_links; ++i) {
		free_d_type(accum.d_type_array[i]);
	}

	/* if (display_on && (li.N_violations != 0) &&
	   (verbosity > 3) && should_print_messages)
	   printf("P.P. violation in one part of conjunction.\n"); */
	free_sublinkage(sublinkage);
	free_digraph(pi, word_links);
	free_DIS_tree(d_root);
	return li;
}