Beispiel #1
0
def delete_nonderivable_nonterminals(grammar):
	new_grammar = Grammar()
	new_grammar.axiom = grammar.axiom
	new_grammar.terminals = grammar.terminals

	unwatched = list([new_grammar.axiom])
	watched = set()
	while unwatched:
		nonterminal = unwatched[0]
		unwatched = unwatched.remove(nonterminal) or []
		watched.add(nonterminal)

		rules = find_rules_for_nonterminal(grammar.rules, nonterminal)
		for rule in rules:
			for symbol in rule.right_side:
				if isinstance(symbol, Nonterminal):
					if symbol not in watched and symbol not in unwatched:
						unwatched.append(symbol)

	new_grammar.nonterminals = watched

	new_rules = []
	for rule in grammar.rules:
		if rule.left_side[0] in watched:
			new_rules.append(rule)

	new_grammar.rules = new_rules

	return new_grammar	 
Beispiel #2
0
def convert_grammar(grammar, disappearing_nonterminals):
	print "algorithm 1"
	new_grammar = Grammar()

	# build new nonterminals set
	new_grammar.nonterminals = build_new_nonterminals_set(
		grammar, disappearing_nonterminals)

	# find new axiom
	if grammar.axiom in disappearing_nonterminals:
		# language has empty chain
		new_grammar.axiom = Nonterminal(grammar.axiom.name, False)
		new_grammar.nonterminals.add(new_grammar.axiom)
		new_grammar.nonterminals.remove(grammar.axiom)
	else:
		new_grammar.axiom = grammar.axiom

	# build new rules
	new_grammar.rules = build_new_rules(
		grammar, disappearing_nonterminals, new_grammar.nonterminals)

	# copy terminals	
	new_grammar.terminals = set(grammar.terminals)
	return new_grammar
Beispiel #3
0
def delete_useless_nonterminals(grammar):
	new_rules = list(grammar.rules)
	new_nonterminals = set(grammar.nonterminals)

	while True:
		useless_nonterminals = find_useless_nonterminals(new_rules)
		if not useless_nonterminals:
			break

		new_rules = delete_useless_nonterminals_from_rules(new_rules, useless_nonterminals)
		new_rules = delete_useless_nonterminals_rules(new_rules, useless_nonterminals)
		new_nonterminals.difference_update(useless_nonterminals) 

	new_grammar = Grammar()
	new_grammar.axiom = grammar.axiom
	new_grammar.terminals = set(grammar.terminals)
	new_grammar.nonterminals = new_nonterminals
	new_grammar.rules = new_rules
	return new_grammar
Beispiel #4
0
def convert_to_greibach(grammar):
	print "algorithm 3"
	converted_grammar = delete_empty_rules(grammar)
	print "converted grammar:"
	print converted_grammar
	
	new_grammar = Grammar()
	new_grammar.axiom = converted_grammar.axiom	
	new_grammar.terminals = set(converted_grammar.terminals)	

	sorted_nonterminals = sort_nonterminals(
		converted_grammar.nonterminals, converted_grammar.rules)
	print "sorted nonterminals:", [str(s) for s in sorted_nonterminals]
	new_grammar.nonterminals = set(sorted_nonterminals)

	# rebuild rules
	nonterminal = sorted_nonterminals[-1]
	new_rules = find_rules_for_nonterminal(converted_grammar.rules, nonterminal)
	for idx in range(len(sorted_nonterminals)  - 2, -1, -1):
		nonterminal = sorted_nonterminals[idx]
		rules = find_rules_for_nonterminal(converted_grammar.rules, nonterminal)
		for rule in rules:
			if isinstance(rule.right_side[0], Nonterminal):
				new_rules.extend(replace_rule(new_rules, rule))
			else:
				new_rules.append(rule)

	# add rules for terminals
	for terminal in converted_grammar.terminals:
		new_nonterminal = Nonterminal("X{%s}" % str(terminal))
		new_grammar.nonterminals.add(new_nonterminal)
		new_rules.append(Rule([new_nonterminal], [terminal]))

		# replace nonleft terminal to new nonterminals
		for rule in new_rules:
			rule =replace_nonleft_terminal_to_nonterminal(rule, terminal, new_nonterminal)

	new_grammar.rules = new_rules
	
	print "grammar:", new_grammar
		
	return delete_nonderivable_nonterminals(new_grammar)
Beispiel #5
0
def build_new_grammar(grammar):
	new_grammar = Grammar()
	new_grammar.terminals = set(grammar.terminals)
	new_grammar.axiom = ComplexNonterminal(
		[grammar.axiom], grammar.axiom.is_nullable)

	new_rules = []
	unwatched, watched = [new_grammar.axiom], set()
	while unwatched:
		complex_nonterminal = unwatched[0]
		unwatched.remove(complex_nonterminal)
		watched.add(complex_nonterminal)

		if complex_nonterminal.starts_with_nonterminal():
			new_rules.extend(build_rules_starts_with_nonterminal(
				grammar.rules, complex_nonterminal, watched, unwatched))
		elif complex_nonterminal.starts_with_terminal():
			new_rules.extend(build_rules_starts_with_terminal(
				grammar.rules, complex_nonterminal, watched, unwatched))
					
	new_grammar.rules = new_rules
	new_grammar.nonterminals = watched
	return new_grammar
Beispiel #6
0
from grammar import (Symbol , EmptySymbol,Terminal,
					 Nonterminal, Rule, Grammar)
from conversion import (has_empty_chain, convert_grammar, find_disappearing_nonterminals,
				   delete_empty_rules, delete_useless_nonterminals, convert_to_greibach)


grammar = Grammar()

S = Nonterminal('S')
A = Nonterminal('A')
B = Nonterminal('B')
grammar.nonterminals.update([A, B, S])

grammar.axiom = S

a = Terminal('a')
b = Terminal('b')
grammar.terminals.update([a, b])

e = EmptySymbol()

grammar.rules.append(Rule([S], [A, B]))
grammar.rules.append(Rule([A], [a, A]))
grammar.rules.append(Rule([A], [e]))
grammar.rules.append(Rule([B], [b, A]))
grammar.rules.append(Rule([B], [e]))

print "grammar:\n", grammar

#disappearing_nonterminals = find_disappearing_nonterminals(grammar)
#new_grammar = convert_grammar(grammar, disappearing_nonterminals)