Im Folgenden sehen Sie die Klassenhierarchie der einzelnen Bestandteile des
Setty-Syntaxbaumes.
Node
Diese Klasse ist die abstrakte Basisklasse aller Knoten des Syntaxbaumes.
SetNode
Diese Klasse ist die abstrakte Basisklasse aller Knoten, welche jeweils zur Repräsentation einer Menge vorgesehen sind.
LowerSetNode
Diese Klasse wird zur Bildung einer Menge der Form
„{x|x<limit}”
benötigt.
Mit ihr kann gegebenenfalls die Produktion
„To”
repräsentiert werden.
LowerEqualSetNode
Diese Klasse wird zur Bildung einer Menge der Form
„{x|x<limit oder x=limit}”
benötigt.
Mit ihr kann gegebenenfalls die Produktion
„To”
repräsentiert werden.
GreaterSetNode
Diese Klasse wird zur Bildung einer Menge der Form
„{x|x>limit}”
benötigt.
Mit ihr kann gegebenenfalls die Produktion
„From”
repräsentiert werden.
GreaterEqualSetNode
Diese Klasse wird zur Bildung einer Menge der Form
„{x|x>limit oder x=limit}”
benötigt.
Mit ihr kann gegebenenfalls die Produktion
„From”
repräsentiert werden.
ElementsSetNode
(Elementmenge)
Diese Klasse wird zur Bildung einer Menge der Form
„{z1,z2,...,zn}”
benötigt.
Mit ihr kann gegebenenfalls die Produktion
„Set”
repräsentiert werden.
UnionSetNode
(Vereinigung mehrerer Mengen)
Diese Klasse wird zur Bildung einer Menge der Form
„s1 v s2 v ... v sn”
benötigt.
Mit ihr kann gegebenenfalls die Produktion
„SetU”
repräsentiert werden.
IntersectionSetNode
(Durchschnitt mehrerer Mengen)
Diese Klasse wird zur Bildung einer Menge der Form
„s1 n s2 n ... n sn”
benötigt.
Mit ihr kann gegebenenfalls die Produktion
„SetI”
repräsentiert werden.
DifferenceSetNode
(Mengendifferenz zweier Mengen)
Diese Klasse wird zur Bildung einer Menge der Form
„s1 \ s2”
benötigt.
Mit ihr kann gegebenenfalls die Produktion
„SetD”
repräsentiert werden.
ComplementSetNode
(Komplement einer Menge)
Diese Klasse wird zur Bildung einer Menge der Form
„C(s)”
benötigt.
Mit ihr kann gegebenenfalls die Produktion
„Set”
repräsentiert werden.
ProgramNode
Diese Klasse wird zur Repräsentation eines gesamten
Setty-Programms.
Mit dieser Klasse wird der Wurzelknoten des Syntaxbaumes erzeugt.
Die eben beschriebenen Klassen werden im Folgenden implementiert.
/**
* Diese Klasse ist eine abstrakte Basisklasse zur Erzeugung von
* Knoten des Setty-Syntaxbaumes.
*/
abstract public class Node {
/**
* Generiert eine Phrase in der Sprache C.
* @return C-Code als Zeichenkette.
*/
abstract public String generateCCode();
/**
* Generiert eine Phrase in der Sprache Pascal.
* @return Pascal-Code als Zeichenkette.
*/
abstract public String generatePascalCode();
/**
* Generiert eine Phrase in der Sprache SML.
* @return SML-Code als Zeichenkette.
*/
abstract public String generateSmlCode();
/**
* Reine Hilfsmethode zur Konvertierung von double in SML-real.
* @param element Ein Java-Double-Wert.
* @return Den entsprechende SML-Wert als Zeichenkette.
*/
protected String doubleToSmlReal(double element) {
String result = "";
if (element < 0.0) {
result += '~';
}
result += Math.abs(element);
return result;
}
}
/**
* Diese Klasse ist eine abstrakte Basisklasse zur Erzeugung einer Menge
* des Setty-Syntaxbaumes.
*/
abstract public class SetNode extends Node {
/**
* Prüft, ob ein Wert in der Menge liegt oder nicht.
* @param element Der zu prüfende Wert.
* @return true, falls der Wert in der Menge enthalten ist.
*/
abstract public boolean contains(double element);
}
public class LowerSetNode extends SetNode {
private double limit;
public LowerSetNode(double limit) {
this.limit = limit;
}
public boolean contains(double element) {
return element < limit;
}
public String generateCCode() {
return "element < " + this.limit;
}
public String generatePascalCode() {
return "Element < " + this.limit;
}
public String generateSmlCode() {
return "set (fn x => x < " + this.doubleToSmlReal(this.limit) + ")";
}
}
public class LowerEqualSetNode extends SetNode {
private double limit;
public LowerEqualSetNode(double limit) {
this.limit = limit;
}
public boolean contains(double element) {
return element <= limit;
}
public String generateCCode() {
return "element <= " + this.limit;
}
public String generatePascalCode() {
return "Element <= " + this.limit;
}
public String generateSmlCode() {
return "set (fn x => x <= " + this.doubleToSmlReal(this.limit) + ")";
}
}
public class GreaterSetNode extends SetNode {
private double limit;
public GreaterSetNode(double limit) {
this.limit = limit;
}
public boolean contains(double element) {
return element > limit;
}
public String generateCCode() {
return "element > " + this.limit;
}
public String generatePascalCode() {
return "Element > " + this.limit;
}
public String generateSmlCode() {
return "set (fn x => x > " + this.doubleToSmlReal(this.limit) + ")";
}
}
public class GreaterEqualSetNode extends SetNode {
private double limit;
public GreaterEqualSetNode(double limit) {
this.limit = limit;
}
public boolean contains(double element) {
return element >= limit;
}
public String generateCCode() {
return "element >= " + this.limit;
}
public String generatePascalCode() {
return "Element >= " + this.limit;
}
public String generateSmlCode() {
return "set (fn x => x >= " + this.doubleToSmlReal(this.limit) + ")";
}
}
import java.util.LinkedList;
import java.util.Iterator;
import java.util.ListIterator;
public class ElementsSetNode extends SetNode {
private LinkedList elements;
public ElementsSetNode() {
this.elements = new LinkedList();
}
public void addElement(double element) {
if (!this.elements.contains(new Double(element))) {
this.elements.add(new Double(element));
}
}
public boolean contains(double element) {
Iterator iterator = this.elements.listIterator();
while (iterator.hasNext()) {
Double nextElement = (Double)iterator.next();
if (nextElement.doubleValue() == element) {
return true;
}
}
return false;
}
public String generateCCode() {
String result = "";
if (this.elements.size() <= 0) { // die leere Menge
result += "0";
} else if (this.elements.size() == 1) { // einelementige Menge
result += "element == " + this.elements.getFirst();
} else { // mehrelementige Menge
ListIterator listIterator = this.elements.listIterator();
while (listIterator.hasNext()) {
if (listIterator.hasPrevious()) {
result += " || ";
}
result += "(element == " + listIterator.next() + ")";
}
}
return result;
}
public String generatePascalCode() {
String result = "";
if (this.elements.size() <= 0) { // die leere Menge
result += "false";
} else if (this.elements.size() == 1) { // einelementige Menge
result += "Element = " + this.elements.getFirst();
} else { // mehrelementige Menge
ListIterator listIterator = this.elements.listIterator();
while (listIterator.hasNext()) {
if (listIterator.hasPrevious()) {
result += " or ";
}
result += "(Element = " + listIterator.next() + ")";
}
}
return result;
}
public String generateSmlCode() {
String result = "elemN [";
ListIterator listIterator = this.elements.listIterator();
while (listIterator.hasNext()) {
if (listIterator.hasPrevious()) {
result += ", ";
}
Double nextElement = (Double)listIterator.next();
result += this.doubleToSmlReal(nextElement.doubleValue());
}
result += "]";
return result;
}
}
import java.util.LinkedList;
import java.util.Iterator;
import java.util.ListIterator;
public class UnionSetNode extends SetNode {
private LinkedList setNodes;
public UnionSetNode() {
this.setNodes = new LinkedList();
}
public void addSetNode(SetNode setNode) {
if (setNode != null) {
this.setNodes.add(setNode);
}
}
public boolean contains(double element) {
Iterator iterator = this.setNodes.listIterator();
while (iterator.hasNext()) {
if (((SetNode)iterator.next()).contains(element)) {
return true;
}
}
return false;
}
public String generateCCode() {
String result = "";
if (this.setNodes.size() <= 0) {
result += "0";
} else if (this.setNodes.size() == 1) {
result += ((SetNode)this.setNodes.getFirst()).generateCCode();
} else {
ListIterator listIterator = this.setNodes.listIterator();
while (listIterator.hasNext()) {
if (listIterator.hasPrevious()) {
result += " || ";
}
result += "(";
result += ((SetNode)listIterator.next()).generateCCode();
result += ")";
}
}
return result;
}
public String generatePascalCode() {
String result = "";
if (this.setNodes.size() <= 0) {
result += "false";
} else if (this.setNodes.size() == 1) {
result += ((SetNode)this.setNodes.getFirst()).generatePascalCode();
} else {
ListIterator listIterator = this.setNodes.listIterator();
while (listIterator.hasNext()) {
if (listIterator.hasPrevious()) {
result += " or ";
}
result += "(";
result += ((SetNode)listIterator.next()).generatePascalCode();
result += ")";
}
}
return result;
}
public String generateSmlCode() {
String result = "unionN [";
ListIterator listIterator = this.setNodes.listIterator();
while (listIterator.hasNext()) {
if (listIterator.hasPrevious()) {
result += ", ";
}
result += "(" + ((SetNode)listIterator.next()).generateSmlCode() + ")";
}
result += "]";
return result;
}
}
import java.util.LinkedList;
import java.util.Iterator;
import java.util.ListIterator;
public class IntersectionSetNode extends SetNode {
private LinkedList setNodes;
public IntersectionSetNode() {
this.setNodes = new LinkedList();
}
public void addSetNode(SetNode setNode) {
if (setNode != null) {
this.setNodes.add(setNode);
}
}
public boolean contains(double element) {
Iterator iterator = this.setNodes.listIterator();
while (iterator.hasNext()) {
if (!((SetNode)iterator.next()).contains(element)) {
return false;
}
}
return (this.setNodes.size() > 0);
}
public String generateCCode() {
String result = "";
if (this.setNodes.size() <= 0) {
result += "0";
} else if (this.setNodes.size() == 1) {
result += ((SetNode)this.setNodes.getFirst()).generateCCode();
} else {
ListIterator listIterator = this.setNodes.listIterator();
while (listIterator.hasNext()) {
if (listIterator.hasPrevious()) {
result += " && ";
}
result += "(";
result += ((SetNode)listIterator.next()).generateCCode();
result += ")";
}
}
return result;
}
public String generatePascalCode() {
String result = "";
if (this.setNodes.size() <= 0) {
result += "false";
} else if (this.setNodes.size() == 1) {
result += ((SetNode)this.setNodes.getFirst()).generatePascalCode();
} else {
ListIterator listIterator = this.setNodes.listIterator();
while (listIterator.hasNext()) {
if (listIterator.hasPrevious()) {
result += " and ";
}
result += "(";
result += ((SetNode)listIterator.next()).generatePascalCode();
result += ")";
}
}
return result;
}
public String generateSmlCode() {
String result = "interN [";
ListIterator listIterator = this.setNodes.listIterator();
while (listIterator.hasNext()) {
if (listIterator.hasPrevious()) {
result += ", ";
}
result += "(" + ((SetNode)listIterator.next()).generateSmlCode() + ")";
}
result += "]";
return result;
}
}
public class DifferenceSetNode extends SetNode {
private SetNode setNode1;
private SetNode setNode2;
public DifferenceSetNode(SetNode setNode1, SetNode setNode2) {
this.setNode1 = setNode1;
this.setNode2 = setNode2;
}
public boolean contains(double element) {
return this.setNode1.contains(element) & (!this.setNode2.contains(element));
}
public String generateCCode() {
SetNode notNode2 = new ComplementSetNode(this.setNode2);
String result = "";
result += "(" + notNode2.generateCCode() + ")";
result += " && ";
result += "(" + this.setNode1.generateCCode() + ")";
return result;
}
public String generatePascalCode() {
SetNode notNode2 = new ComplementSetNode(this.setNode2);
String result = "";
result += "(" + notNode2.generatePascalCode() + ")";
result += " and ";
result += "(" + this.setNode1.generatePascalCode() + ")";
return result;
}
public String generateSmlCode() {
String result = "minus (" + this.setNode1.generateSmlCode() + ") ";
result += "(" + this.setNode2.generateSmlCode() + ")";
return result;
}
}
public class ComplementSetNode extends SetNode {
private SetNode setNode;
public ComplementSetNode(SetNode setNode) {
this.setNode = setNode;
}
public boolean contains(double element) {
return !this.setNode.contains(element);
}
public String generateCCode() {
return "!(" + this.setNode.generateCCode() + ")";
}
public String generatePascalCode() {
return "not(" + this.setNode.generatePascalCode() + ")";
}
public String generateSmlCode() {
return "compl (" + this.setNode.generateSmlCode() + ")";
}
}
public class ProgramNode extends Node {
private double element;
private boolean not;
private SetNode setNode;
public ProgramNode(double element, boolean not, SetNode setNode) {
this.element = element;
this.not = not;
this.setNode = setNode;
}
public String getResult() {
SetNode node = this.setNode;
if (this.not) {
node = new ComplementSetNode(node);
}
if (node.contains(this.element)) {
return "yes";
} else {
return "no";
}
}
public String generateCCode() {
SetNode node = this.setNode;
if (this.not) {
node = new ComplementSetNode(node);
}
String result = "";
result += "#include <stdio.h>\r\n";
result += "\r\n";
result += "int main(void) {\r\n";
result += " \r\n";
result += " double element = " + this.element + ";\r\n";
result += " \r\n";
result += " if (" + node.generateCCode() + ") {\r\n";
result += " printf(\"yes\\n\");\r\n";
result += " } else {\r\n";
result += " printf(\"no\\n\");\r\n";
result += " }\r\n";
result += " \r\n";
result += " return 0;\r\n";
result += "}";
return result;
}
public String generatePascalCode() {
SetNode node = this.setNode;
if (this.not) {
node = new ComplementSetNode(node);
}
String result = "";
result += "program a_setty;\r\n";
result += "\r\n";
result += "var Element: Extended;\r\n";
result += "\r\n";
result += "begin\r\n";
result += " \r\n";
result += " Element := " + this.element + ";\r\n";
result += " \r\n";
result += " if " + node.generatePascalCode() + "\r\n";
result += " then writeln('yes')\r\n";
result += " else writeln('no');\r\n";
result += " \r\n";
result += "end.";
return result;
}
public String generateSmlCode() {
String result = "";
result += "abstype 'a SET = Set of 'a -> bool\r\n";
result += " with\r\n";
result += " fun set b = Set b\r\n";
result += "\r\n";
result += " val EmptySet = Set (fn x => false)\r\n";
result += " val RealSet = Set (fn x => true)\r\n";
result += "\r\n";
result += " fun union (Set s) (Set t) = Set (fn x => s x orelse t x)\r\n";
result += " fun unionN [] = EmptySet\r\n";
result += " | unionN (s::sl) = union s (unionN sl)\r\n";
result += "\r\n";
result += " fun inter (Set s) (Set t) = Set (fn x => s x andalso t x)\r\n";
result += " fun interN [] = RealSet\r\n";
result += " | interN (s::sl) = inter s (interN sl)\r\n";
result += "\r\n";
result += " fun elem e = Set (fn x => Real.==(x, e))\r\n";
result += " fun elemN [] = EmptySet\r\n";
result += " | elemN (e::el) = union (elem e) (elemN el)\r\n";
result += "\r\n";
result += " fun compl (Set s) = Set (not o s)\r\n";
result += "\r\n";
result += " fun minus S T = inter (compl T) S\r\n";
result += "\r\n";
result += " fun isin e (Set s) = s e\r\n";
result += " fun isnotin e (Set s) = (not o s) e\r\n";
result += " end;\r\n";
result += "\r\n";
result += "fun yesorno true = print(\"yes\\n\")\r\n";
result += " | yesorno false = print(\"no\\n\");\r\n";
result += "\r\n";
result += "yesorno (";
if (this.not) {
result += "isnotin ";
} else {
result += "isin ";
}
result += this.doubleToSmlReal(this.element);
result += " (" + this.setNode.generateSmlCode() + "));";
return result;
}
}