more Cosmas feautres: BEG, END, ALL, NHIT
diff --git a/src/main/java/de/ids_mannheim/korap/query/serialize/AbstractSyntaxTree.java b/src/main/java/de/ids_mannheim/korap/query/serialize/AbstractSyntaxTree.java
index cf19977..5ca3cb8 100644
--- a/src/main/java/de/ids_mannheim/korap/query/serialize/AbstractSyntaxTree.java
+++ b/src/main/java/de/ids_mannheim/korap/query/serialize/AbstractSyntaxTree.java
@@ -2,10 +2,12 @@
import java.util.Map;
+import de.ids_mannheim.korap.util.QueryException;
+
public abstract class AbstractSyntaxTree {
public abstract Map<String, Object> getRequestMap();
- public abstract void process(String query);
+ public abstract void process(String query) throws QueryException;
}
diff --git a/src/main/java/de/ids_mannheim/korap/query/serialize/CosmasTree.java b/src/main/java/de/ids_mannheim/korap/query/serialize/CosmasTree.java
index 0a34539..49e948d 100644
--- a/src/main/java/de/ids_mannheim/korap/query/serialize/CosmasTree.java
+++ b/src/main/java/de/ids_mannheim/korap/query/serialize/CosmasTree.java
@@ -17,6 +17,7 @@
import de.ids_mannheim.korap.query.cosmas2.c2psLexer;
import de.ids_mannheim.korap.query.cosmas2.c2psParser;
import de.ids_mannheim.korap.query.serialize.AbstractSyntaxTree;
+import de.ids_mannheim.korap.util.QueryException;
/**
* Map representation of CosmasII syntax tree as returned by ANTLR
@@ -104,8 +105,9 @@
*
* @param tree The syntax tree as returned by ANTLR
* @param parser The ANTLR parser instance that generated the parse tree
+ * @throws QueryException
*/
- public CosmasTree(String query) {
+ public CosmasTree(String query) throws QueryException {
this.query = query;
process(query);
System.out.println(requestMap.get("query"));
@@ -144,8 +146,16 @@
}
@Override
- public void process(String query) {
- Tree tree = parseCosmasQuery(query);
+ public void process(String query) throws QueryException {
+ Tree tree = null;
+ try {
+ tree = parseCosmasQuery(query);
+ } catch (RecognitionException e) {
+ throw new QueryException("Your query could not be processed. Please make sure it is well-formed.");
+ } catch (NullPointerException e) {
+ throw new QueryException("Your query could not be processed. Please make sure it is well-formed.");
+ }
+
System.out.println("Processing Cosmas");
prepareContext();
processNode(tree);
@@ -342,6 +352,9 @@
proxGroup.put("relation", "distance");
objectStack.push(proxGroup);
stackedObjects++;
+ if (openNodeCats.get(1).equals("OPALL")) proxGroup.put("match", "all");
+ else if (openNodeCats.get(1).equals("OPNHIT")) proxGroup.put("match", "between");
+ else proxGroup.put("match", "operands");
ArrayList<Object> constraints = new ArrayList<Object>();
String subtype = typ.getChild(0).toStringTree().equals("PROX") ? "incl" : "excl";
proxGroup.put("@subtype", subtype);
@@ -355,7 +368,7 @@
String max = dist_list.getChild(0).getChild(1).getChild(1).toStringTree();
String meas = dist_list.getChild(0).getChild(2).getChild(0).toStringTree();
if (min.equals("VAL0")) {
- min=max;
+ min="0";
}
LinkedHashMap<String, Object> distance = new LinkedHashMap<String, Object>();
distance.put("@type", "korap:distance");
@@ -409,16 +422,14 @@
posgroup.put("@type", "korap:group");
String relation = nodeCat.equals("OPIN") ? "position" : "overlap";
posgroup.put("relation", relation);
- String position = "";
- // add optional position info, if present
- if (QueryUtils.getNodeCat(node.getChild(0)).equals("POS")) {
- String posinfo = node.getChild(0).getChild(0).toStringTree();
- position = posinfo.equals("L") ? "startswith" : "endswith";
+ if (nodeCat.equals("OPIN")) {
+ parseOPINOptions(node, posgroup);
} else {
- position = nodeCat.equals("OPIN") ? "contains" : "full";
+ parseOPOVOptions(node, posgroup);
}
- posgroup.put("position", position);
+
+
ArrayList<Object> posoperands = new ArrayList<Object>();
posgroup.put("operands", posoperands);
objectStack.push(posgroup);
@@ -430,7 +441,8 @@
putIntoSuperObject(shrinkgroup, 1);
}
- // wrap the first argument of an #IN operator in a class group
+
+ // Wrap the first argument of an #IN operator in a class group
if (nodeCat.equals("ARG1") && (openNodeCats.get(1).equals("OPIN") || openNodeCats.get(1).equals("OPOV"))) {
// Step I: create group
LinkedHashMap<String, Object> classGroup = new LinkedHashMap<String, Object>();
@@ -445,30 +457,16 @@
if (nodeCat.equals("OPALL") || nodeCat.equals("OPNHIT")) {
- // Step I: create group
- LinkedHashMap<String, Object> allgroup = new LinkedHashMap<String, Object>();
- allgroup.put("@type", "korap:group");
- String scope = nodeCat.equals("OPALL") ? "all" : "nhit";
- allgroup.put("relation", scope);
- // add optional position info, if present
- if (QueryUtils.getNodeCat(node.getChild(0)).equals("POS")) {
- allgroup.put("position", node.getChild(0).getChild(0).toStringTree());
- }
- allgroup.put("operands", new ArrayList<Object>());
- objectStack.push(allgroup);
- stackedObjects++;
-
- // Step II: decide where to put
- putIntoSuperObject(allgroup, 1);
+// proxGroupMatching = nodeCat.equals("OPALL") ? "all" : "exlcude";
}
if (nodeCat.equals("OPEND") || nodeCat.equals("OPBEG")) {
// Step I: create group
LinkedHashMap<String, Object> bedgroup = new LinkedHashMap<String, Object>();
bedgroup.put("@type", "korap:group");
- bedgroup.put("relation", "reduction");
- String reduction = nodeCat.equals("OPEND") ? "end" : "begin";
- bedgroup.put("reduction", reduction);
+ bedgroup.put("relation", "shrink");
+ String reduction = nodeCat.equals("OPBEG") ? "first" : "last";
+ bedgroup.put("shrink", reduction);
bedgroup.put("operands", new ArrayList<Object>());
objectStack.push(bedgroup);
stackedObjects++;
@@ -501,12 +499,24 @@
objectsToPop.push(stackedObjects);
- // recursion until 'query' node (root of tree) is processed
+ /*
+ ****************************************************************
+ ****************************************************************
+ * recursion until 'request' node (root of tree) is processed *
+ ****************************************************************
+ ****************************************************************
+ */
for (int i=0; i<node.getChildCount(); i++) {
Tree child = node.getChild(i);
processNode(child);
}
+ /*
+ **************************************************************
+ * Stuff that happens after processing the children of a node *
+ **************************************************************
+ */
+
// remove sequence from object stack if node is implicitly sequenced
if (sequencedNodes.size()>0) {
if (node == sequencedNodes.getFirst()) {
@@ -527,12 +537,6 @@
}
objectsToPop.pop();
-
-
-
-
-
-
if (nodeCat.equals("ARG2") && openNodeCats.get(1).equals("OPNOT")) {
negate = false;
}
@@ -541,11 +545,116 @@
}
+
+
+ private void parseOPINOptions(Tree node, LinkedHashMap<String, Object> posgroup) {
+ Tree posnode = QueryUtils.getFirstChildWithCat(node, "POS");
+ Tree rangenode = QueryUtils.getFirstChildWithCat(node, "RANGE");
+ Tree exclnode = QueryUtils.getFirstChildWithCat(node, "EXCL");
+ Tree groupnode = QueryUtils.getFirstChildWithCat(node, "GROUP");
+ boolean negatePosition = false;
+
+ String position = "";
+ if (posnode != null) {
+ String value = posnode.getChild(0).toStringTree();
+ position = translateTextAreaArgument(value);
+ if (value.equals("N")) {
+ negatePosition = !negatePosition;
+ }
+ } else {
+ position = "contains";
+ }
+ posgroup.put("position", position);
+ position = openNodeCats.get(1).equals("OPIN") ? "contains" : "full";
+
+ if (rangenode != null) {
+ String range = rangenode.getChild(0).toStringTree();
+ posgroup.put("range", range.toLowerCase());
+ }
+
+ if (exclnode != null) {
+ if (exclnode.getChild(0).toStringTree().equals("YES")) {
+ negatePosition = !negatePosition;
+ }
+ }
+
+ if (negatePosition) {
+ posgroup.put("@subtype", "excl");
+ }
+
+ if (groupnode != null) {
+ String grouping = groupnode.getChild(0).toStringTree().equals("MAX") ? "true" : "false";
+ posgroup.put("grouping", grouping);
+ }
+ }
+
+ private void parseOPOVOptions(Tree node, LinkedHashMap<String, Object> posgroup) {
+ Tree posnode = QueryUtils.getFirstChildWithCat(node, "POS");
+ Tree exclnode = QueryUtils.getFirstChildWithCat(node, "EXCL");
+ Tree groupnode = QueryUtils.getFirstChildWithCat(node, "GROUP");
+
+ String position = "";
+ if (posnode != null) {
+ String value = posnode.getChild(0).toStringTree();
+ position = translateTextAreaArgument(value);
+ } else {
+ position = "any";
+ }
+ posgroup.put("position", position);
+ position = openNodeCats.get(1).equals("OPIN") ? "contains" : "full";
+
+ if (exclnode != null) {
+ if (exclnode.getChild(0).toStringTree().equals("YES")) {
+ posgroup.put("@subtype", "excl");
+ }
+ }
+ if (groupnode != null) {
+ String grouping = groupnode.getChild(0).toStringTree().equals("MAX") ? "true" : "false";
+ posgroup.put("grouping", grouping);
+ }
+
+ }
+
+ /**
+ * Translates the text area specifications (position option arguments) to terms used in serealisation.
+ * For the allowed argument types and their values for OPIN and OPOV, see
+ * http://www.ids-mannheim.de/cosmas2/win-app/hilfe/suchanfrage/eingabe-grafisch/syntax/ARGUMENT_I.html or
+ * http://www.ids-mannheim.de/cosmas2/win-app/hilfe/suchanfrage/eingabe-grafisch/syntax/ARGUMENT_O.html, respectively.
+ * @param argument
+ * @return
+ */
+ private String translateTextAreaArgument(String argument) {
+ String position = "";
+ switch (argument) {
+ case "L":
+ position = "startswith";
+ break;
+ case "R":
+ position = "endswith";
+ break;
+ case "F":
+ position = "leftrightmatch";
+ break;
+ case "FE":
+ position = "ident";
+ break;
+ case "FI":
+ position = "leftrightmatch-noident";
+ break;
+ case "N": // for OPIN only - exclusion constraint formulated in parseOPINOptions
+ position = "leftrightmatch";
+ break;
+ case "X": // for OPOV only
+ position = "residual";
+ break;
+ }
+ return position;
+ }
+
@SuppressWarnings("unchecked")
private void putIntoSuperObject(LinkedHashMap<String, Object> object, int objStackPosition) {
if (objectStack.size()>objStackPosition) {
ArrayList<Object> topObjectOperands = (ArrayList<Object>) objectStack.get(objStackPosition).get("operands");
- System.out.println("XXX: "+invertedOperandsLists.contains(topObjectOperands));
if (!invertedOperandsLists.contains(topObjectOperands)) {
topObjectOperands.add(object);
} else {
@@ -562,27 +671,20 @@
}
- private static Tree parseCosmasQuery(String p) {
+ private static Tree parseCosmasQuery(String p) throws RecognitionException {
Tree tree = null;
- ANTLRStringStream
- ss = new ANTLRStringStream(p);
- c2psLexer
- lex = new c2psLexer(ss);
- org.antlr.runtime.CommonTokenStream tokens = //v3
- new org.antlr.runtime.CommonTokenStream(lex);
+ ANTLRStringStream ss = new ANTLRStringStream(p);
+ c2psLexer lex = new c2psLexer(ss);
+ org.antlr.runtime.CommonTokenStream tokens = new org.antlr.runtime.CommonTokenStream(lex); //v3
cosmasParser = new c2psParser(tokens);
- c2psParser.c2ps_query_return
- c2Return = null;
- try
- {
- c2Return = cosmasParser.c2ps_query(); // statt t().
- }
- catch (RecognitionException e)
- {
- e.printStackTrace();
- }
+ c2psParser.c2ps_query_return c2Return = cosmasParser.c2ps_query(); // statt t().
// AST Tree anzeigen:
tree = (Tree)c2Return.getTree();
+
+ String treestring = tree.toStringTree();
+ if (treestring.contains("<mismatched token") || treestring.contains("<error") || treestring.contains("<unexpected")) {
+ throw new RecognitionException();
+ }
return tree;
}
@@ -591,7 +693,7 @@
*/
public static void main(String[] args) {
/*
- * For testing
+ * For debugging
*/
String[] queries = new String[] {
/* COSMAS 2 */
@@ -618,7 +720,7 @@
// "der Mann",
// "Sonne nicht (Mond Stern)",
// "Sonne /+w1:4 Mond",
-//// "wegen #IN(L) <s>"
+// "wegen #IN(L) <s>"
// "#BEG(<s>) /5w,s0 #END(<s>)",
// "der Mann",
// "Mond oder Sterne",
@@ -649,6 +751,14 @@
"wegen #OV #ELEM(S)",
"wegen #IN #ELEM(S)",
// "Sonne oder Mond"
+ "wegen #IN('FE,ALL,%,MIN') <s>",
+ "wegen #IN('FE,ALL,MIN') <s>",
+ "wegen #IN <s>",
+ "wegen #IN(L) <s>",
+ "wegen #IN(%, L) <s>",
+ "wegen #OV('FE,%,MIN') <s>",
+ "#BEG(der /+w1:2 Mann)",
+ "#BEG(der Mann /10w Mann)"
/*
* TODO
* http://www.ids-mannheim.de/cosmas2/win-app/hilfe/suchanfrage/eingabe-grafisch/syntax/ARGUMENT_I.html
@@ -660,8 +770,15 @@
for (String q : queries) {
try {
System.out.println(q);
- System.out.println(parseCosmasQuery(q).toStringTree());
- CosmasTree act = new CosmasTree(q);
+ try {
+ System.out.println(parseCosmasQuery(q).toStringTree());
+ @SuppressWarnings("unused")
+ CosmasTree act = new CosmasTree(q);
+ } catch (RecognitionException e) {
+ e.printStackTrace();
+ } catch (QueryException e) {
+ e.printStackTrace();
+ }
System.out.println();
} catch (NullPointerException npe) {
diff --git a/src/main/java/de/ids_mannheim/korap/query/serialize/PoliqarpPlusTree.java b/src/main/java/de/ids_mannheim/korap/query/serialize/PoliqarpPlusTree.java
index fd0c34a..bd58449 100644
--- a/src/main/java/de/ids_mannheim/korap/query/serialize/PoliqarpPlusTree.java
+++ b/src/main/java/de/ids_mannheim/korap/query/serialize/PoliqarpPlusTree.java
@@ -362,8 +362,20 @@
// add token to sequence only if it is not an only child (in that case, cq_segments has already added the info and is just waiting for the values from "field")
// take into account a possible 'occ' child
if (node.getParent().getChildCount()>1) {
- ArrayList<Object> topSequenceOperands = (ArrayList<Object>) objectStack.get(onTopOfObjectStack).get("operands");
- topSequenceOperands.add(token);
+ if (node.getText().equals("[]")) {
+ LinkedHashMap<String, Object> sequence = objectStack.get(onTopOfObjectStack);
+ String offsetStr = (String) sequence.get("offset");
+ if (offsetStr == null) {
+ sequence.put("offset", "1");
+ } else {
+ Integer offset = Integer.parseInt(offsetStr);
+ sequence.put("offset", offset+1);
+ }
+
+ } else {
+ ArrayList<Object> topSequenceOperands = (ArrayList<Object>) objectStack.get(onTopOfObjectStack).get("operands");
+ topSequenceOperands.add(token);
+ }
}
}
@@ -503,18 +515,23 @@
objectStack.push(token);
stackedObjects++;
// Step II: fill object (token values) and put into containing sequence
- token.put("@type", "korap:token");
- String word = node.getChild(0).toStringTree(poliqarpParser);
- LinkedHashMap<String,Object> tokenValues = new LinkedHashMap<String,Object>();
- token.put("@value", tokenValues);
- tokenValues.put("@type", "korap:term");
- tokenValues.put("@value", "orth:"+word);
- tokenValues.put("relation", "=");
- // add token to sequence only if it is not an only child (in that case, sq_segments has already added the info and is just waiting for the values from "field")
- if (node.getParent().getChildCount()>1) {
- ArrayList<Object> topSequenceOperands = (ArrayList<Object>) objectStack.get(1).get("operands");
- topSequenceOperands.add(token);
+ if (node.getText().equals("[]")) {
+
+ } else {
+ token.put("@type", "korap:token");
+ String word = node.getChild(0).toStringTree(poliqarpParser);
+ LinkedHashMap<String,Object> tokenValues = new LinkedHashMap<String,Object>();
+ token.put("@value", tokenValues);
+ tokenValues.put("@type", "korap:term");
+ tokenValues.put("@value", "orth:"+word);
+ tokenValues.put("relation", "=");
+ // add token to sequence only if it is not an only child (in that case, sq_segments has already added the info and is just waiting for the values from "field")
+ if (node.getParent().getChildCount()>1) {
+ ArrayList<Object> topSequenceOperands = (ArrayList<Object>) objectStack.get(1).get("operands");
+ topSequenceOperands.add(token);
+ }
}
+ System.out.println(stackedObjects+" "+objectStack);
visited.add(node.getChild(0));
}
@@ -847,7 +864,8 @@
// "([base=bar][base=foo])*",
"([base=a]^[base=b])|[base=c]",
"Baum | Stein",
- "Haus/i"
+ "Haus/i",
+ "startswith(<s>,[]+[base=der][base=Mann])",
};
PoliqarpPlusTree.debug=true;
for (String q : queries) {
diff --git a/src/main/java/de/ids_mannheim/korap/query/serialize/QueryUtils.java b/src/main/java/de/ids_mannheim/korap/query/serialize/QueryUtils.java
index 78300cf..db60b9e 100644
--- a/src/main/java/de/ids_mannheim/korap/query/serialize/QueryUtils.java
+++ b/src/main/java/de/ids_mannheim/korap/query/serialize/QueryUtils.java
@@ -65,6 +65,25 @@
return false;
}
+ public static List<Tree> getChildrenWithCat(Tree node, String nodeCat) {
+ ArrayList<Tree> children = new ArrayList<Tree>();
+ for (int i=0; i<node.getChildCount(); i++) {
+ if (getNodeCat(node.getChild(i)).equals(nodeCat)) {
+ children.add(node.getChild(i));
+ }
+ }
+ return children;
+ }
+
+ public static Tree getFirstChildWithCat(Tree node, String nodeCat) {
+ for (int i=0; i<node.getChildCount(); i++) {
+ if (getNodeCat(node.getChild(i)).equals(nodeCat)) {
+ return node.getChild(i);
+ }
+ }
+ return null;
+ }
+
public static void checkUnbalancedPars(String q) throws QueryException {
int openingPars = StringUtils.countMatches(q, "(");
int closingPars = StringUtils.countMatches(q, ")");
diff --git a/src/test/java/CosmasTreeTest.java b/src/test/java/CosmasTreeTest.java
index 6e67f31..6837282 100644
--- a/src/test/java/CosmasTreeTest.java
+++ b/src/test/java/CosmasTreeTest.java
@@ -3,7 +3,6 @@
import org.junit.Test;
import de.ids_mannheim.korap.query.serialize.CosmasTree;
-import de.ids_mannheim.korap.query.serialize.PoliqarpPlusTree;
import de.ids_mannheim.korap.util.QueryException;
public class CosmasTreeTest {
@@ -34,7 +33,7 @@
@Test
- public void testSingleToken() {
+ public void testSingleToken() throws QueryException {
query="der";
String single1 =
"{@type=korap:token, @value={@type=korap:term, @value=orth:der, relation==}}";
@@ -58,7 +57,7 @@
}
@Test
- public void testSequence() {
+ public void testSequence() throws QueryException {
query="der Mann";
String seq1 =
"{@type=korap:sequence, operands=[" +
@@ -137,7 +136,7 @@
}
@Test
- public void testOPORAND() {
+ public void testOPORAND() throws QueryException {
query="(Sonne oder Mond) und scheint";
String orand1 =
"{@type=korap:group, relation=and, operands=[" +
@@ -166,10 +165,10 @@
}
@Test
- public void testOPPROX() {
+ public void testOPPROX() throws QueryException {
query="Sonne /+w1:4 Mond";
String prox1 =
- "{@type=korap:group, relation=distance, @subtype=incl, " +
+ "{@type=korap:group, relation=distance, match=operands, @subtype=incl, " +
"constraint=[" +
"{@type=korap:distance, measure=w, direction=plus, min=1, max=4}" +
"], " +
@@ -184,7 +183,7 @@
query="Sonne /+w1:4,s0,p1:3 Mond";
String prox2 =
- "{@type=korap:group, relation=distance, @subtype=incl, " +
+ "{@type=korap:group, relation=distance, match=operands, @subtype=incl, " +
"constraint=[" +
"{@type=korap:group, relation=and, operands=[" +
"{@type=korap:distance, measure=w, direction=plus, min=1, max=4}," +
@@ -200,10 +199,44 @@
ppt = new CosmasTree(query);
map = ppt.getRequestMap().get("query").toString();
assertEquals(prox2.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+ query="Sonne %+w1:4,s0,p1:3 Mond";
+ String prox3 =
+ "{@type=korap:group, relation=distance, match=operands, @subtype=excl, " +
+ "constraint=[" +
+ "{@type=korap:group, relation=and, operands=[" +
+ "{@type=korap:distance, measure=w, direction=plus, min=1, max=4}," +
+ "{@type=korap:distance, measure=s, direction=both, min=0, max=0}," +
+ "{@type=korap:distance, measure=p, direction=both, min=1, max=3}" +
+ "]}" +
+ "], " +
+ "operands=[" +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:Sonne, relation==}}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:Mond, relation==}}" +
+ "]" +
+ "}";
+ ppt = new CosmasTree(query);
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(prox3.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+ query="Sonne /+w4 Mond";
+ String prox4 =
+ "{@type=korap:group, relation=distance, match=operands, @subtype=incl, " +
+ "constraint=[" +
+ "{@type=korap:distance, measure=w, direction=plus, min=0, max=4}" +
+ "], " +
+ "operands=[" +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:Sonne, relation==}}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:Mond, relation==}}" +
+ "]" +
+ "}";
+ ppt = new CosmasTree(query);
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(prox4.replaceAll(" ", ""), map.replaceAll(" ", ""));
}
@Test
- public void testOPIN() {
+ public void testOPIN() throws QueryException {
query="wegen #IN <s>";
String opin1 =
"{@type=korap:group, relation=shrink, shrink=1, operands=[" +
@@ -232,6 +265,34 @@
map = ppt.getRequestMap().get("query").toString();
assertEquals(opin2.replaceAll(" ", ""), map.replaceAll(" ", ""));
+ query="wegen #IN(%, L) <s>";
+ String opin3 =
+ "{@type=korap:group, relation=shrink, shrink=1, operands=[" +
+ "{@type=korap:group, relation=position, position=startswith, @subtype=excl, operands=[" +
+ "{@type=korap:elem, @value=s}," +
+ "{@type=korap:group, class=1, operands=[" +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:wegen, relation==}}" +
+ "]}" +
+ "]}" +
+ "]}";
+ ppt = new CosmasTree(query);
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(opin3.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+ query="wegen #IN('FE,ALL,%,MIN') <s>";
+ String opin4 =
+ "{@type=korap:group, relation=shrink, shrink=1, operands=[" +
+ "{@type=korap:group, relation=position, position=ident, range=all, @subtype=excl, grouping=false, operands=[" +
+ "{@type=korap:elem, @value=s}," +
+ "{@type=korap:group, class=1, operands=[" +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:wegen, relation==}}" +
+ "]}" +
+ "]}" +
+ "]}";
+ ppt = new CosmasTree(query);
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(opin4.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
// // position argument is optional
// query="wegen #IN <s>";
// String opin2 =
@@ -259,11 +320,11 @@
}
@Test
- public void testOPOV() {
+ public void testOPOV() throws QueryException {
query="wegen #OV <s>";
String opov1 =
"{@type=korap:group, relation=shrink, shrink=1, operands=[" +
- "{@type=korap:group, relation=overlap, position=full, operands=[" +
+ "{@type=korap:group, relation=overlap, position=any, operands=[" +
"{@type=korap:elem, @value=s}," +
"{@type=korap:group, class=1, operands=[" +
"{@type=korap:token, @value={@type=korap:term, @value=orth:wegen, relation==}}" +
@@ -290,7 +351,7 @@
}
@Test
- public void testOPNOT() {
+ public void testOPNOT() throws QueryException {
query="Sonne nicht Mond";
String opnot1 =
"{@type=korap:group, relation=not, operands=[" +
@@ -303,17 +364,65 @@
}
@Test
- public void testBEG_END() {
+ public void testBEG_END() throws QueryException {
// BEG and END operators
// http://www.ids-mannheim.de/cosmas2/web-app/hilfe/suchanfrage/eingabe-zeile/syntax/links.html
// http://www.ids-mannheim.de/cosmas2/web-app/hilfe/suchanfrage/eingabe-zeile/syntax/rechts.html
// http://www.ids-mannheim.de/cosmas2/web-app/hilfe/suchanfrage/eingabe-zeile/thematische-bsp/bsp-satzlaenge.html
- query="";
+ query="#BEG(der /w3:5 Mann)";
+ String beg1 =
+ "{@type=korap:group, relation=shrink, shrink=first, operands=[" +
+ "{@type=korap:group, relation=distance, match=operands, @subtype=incl, constraint=[" +
+ "{@type=korap:distance, measure=w, direction=both, min=3, max=5}" +
+ "]," +
+ "operands = [" +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:der, relation==}}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:Mann, relation==}}" +
+ "]}" +
+ "]}";
+ ppt = new CosmasTree(query);
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(beg1.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+ query="#BEG(der /w3:5 Mann) /+w10 kommt"; // nesting #BEG() in a distance group
+ String beg2 =
+ "{@type=korap:group, relation=distance, match=operands, @subtype=incl, constraint=[" +
+ "{@type=korap:distance, measure=w, direction=plus, min=0, max=10}" +
+ "], operands=[" +
+ "{@type=korap:group, relation=shrink, shrink=first, operands=[" +
+ "{@type=korap:group, relation=distance, match=operands, @subtype=incl, constraint=[" +
+ "{@type=korap:distance, measure=w, direction=both, min=3, max=5}" +
+ "]," +
+ "operands = [" +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:der, relation==}}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:Mann, relation==}}" +
+ "]}" +
+ "]}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:kommt, relation==}}" +
+ "]}";
+ ppt = new CosmasTree(query);
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(beg2.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+ query="#END(der /w3:5 Mann)";
+ String end1 =
+ "{@type=korap:group, relation=shrink, shrink=last, operands=[" +
+ "{@type=korap:group, relation=distance, match=operands, @subtype=incl, constraint=[" +
+ "{@type=korap:distance, measure=w, direction=both, min=3, max=5}" +
+ "]," +
+ "operands = [" +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:der, relation==}}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=orth:Mann, relation==}}" +
+ "]}" +
+ "]}";
+ ppt = new CosmasTree(query);
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(end1.replaceAll(" ", ""), map.replaceAll(" ", ""));
}
@Test
- public void testELEM() {
+ public void testELEM() throws QueryException {
// http://www.ids-mannheim.de/cosmas2/web-app/hilfe/suchanfrage/eingabe-zeile/syntax/elem.html
query="#ELEM(S)";
String elem1 = "{@type=korap:elem, @value=s}";
@@ -323,11 +432,11 @@
}
@Test
- public void testOPALL() {
+ public void testOPALL() throws QueryException {
query="#ALL(gehen /w1:10 voran)";
String all1 =
- "{@type=korap:group, relation=all, operands=[" +
- "{@type=korap:group, relation=distance, @subtype=incl, " +
+// "{@type=korap:group, relation=all, operands=[" +
+ "{@type=korap:group, relation=distance, match=all, @subtype=incl, " +
"constraint=[" +
"{@type=korap:distance, measure=w, direction=both, min=1, max=10}" +
"], " +
@@ -335,19 +444,20 @@
"{@type=korap:token, @value={@type=korap:term, @value=orth:gehen, relation==}}," +
"{@type=korap:token, @value={@type=korap:term, @value=orth:voran, relation==}}" +
"]" +
- "}" +
- "]}";
+ "}" //+
+// "]}"
+ ;
ppt = new CosmasTree(query);
map = ppt.getRequestMap().get("query").toString();
assertEquals(all1.replaceAll(" ", ""), map.replaceAll(" ", ""));
}
@Test
- public void testOPNHIT() {
+ public void testOPNHIT() throws QueryException {
query="#NHIT(gehen /w1:10 voran)";
String nhit1 =
- "{@type=korap:group, relation=nhit, operands=[" +
- "{@type=korap:group, relation=distance, @subtype=incl, " +
+// "{@type=korap:group, relation=nhit, operands=[" +
+ "{@type=korap:group, relation=distance, match=between, @subtype=incl, " +
"constraint=[" +
"{@type=korap:distance, measure=w, direction=both, min=1, max=10}" +
"], " +
@@ -355,15 +465,16 @@
"{@type=korap:token, @value={@type=korap:term, @value=orth:gehen, relation==}}," +
"{@type=korap:token, @value={@type=korap:term, @value=orth:voran, relation==}}" +
"]" +
- "}" +
- "]}";
+ "}" //+
+// "]}"
+ ;
ppt = new CosmasTree(query);
map = ppt.getRequestMap().get("query").toString();
assertEquals(nhit1.replaceAll(" ", ""), map.replaceAll(" ", ""));
}
@Test
- public void testOPBED() {
+ public void testOPBED() throws QueryException {
query = "#BED(der , sa)";
String bed1 =
"{@type=korap:group, relation=position, position=startswith, operands=[" +
diff --git a/src/test/java/PoliqarpPlusTreeTest.java b/src/test/java/PoliqarpPlusTreeTest.java
index 82f7d72..35753d6 100644
--- a/src/test/java/PoliqarpPlusTreeTest.java
+++ b/src/test/java/PoliqarpPlusTreeTest.java
@@ -59,6 +59,75 @@
String elem2 = "{@type=korap:element, @value=vp}";
assertTrue(equalsQueryContent(elem2, "<vp>"));
}
+
+ @Test
+ public void testEmptyTokens() throws QueryException {
+ // [base=der][][base=Mann]
+ String et1 =
+ "{@type=korap:group, relation=distance, @subtype=incl, constraint=[" +
+ "{@type=korap:distance, measure=w, direction=plus, min=1, max=1}" +
+ "], " +
+ "operands=[" +
+ "{@type=korap:token, @value={@type=korap:term, @value=base:der, relation==}}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=base:Mann, relation==}}" +
+ "]}";
+ ppt = new PoliqarpPlusTree("[base=der][][base=Mann]");
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(et1.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+ // [base=der][][][base=Mann]
+ String et2 =
+ "{@type=korap:group, relation=distance, @subtype=incl, constraint=[" +
+ "{@type=korap:distance, measure=w, direction=plus, min=2, max=2}" +
+ "], " +
+ "operands=[" +
+ "{@type=korap:token, @value={@type=korap:term, @value=base:der, relation==}}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=base:Mann, relation==}}" +
+ "]}";
+ ppt = new PoliqarpPlusTree("[base=der][][base=Mann]");
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(et2.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+ // [base=der][][]?[base=Mann]
+ String et3 =
+ "{@type=korap:group, relation=distance, @subtype=incl, constraint=[" +
+ "{@type=korap:distance, measure=w, direction=plus, min=1, max=2}" +
+ "], " +
+ "operands=[" +
+ "{@type=korap:token, @value={@type=korap:term, @value=base:der, relation==}}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=base:Mann, relation==}}" +
+ "]}";
+ ppt = new PoliqarpPlusTree("[base=der][][]?[base=Mann]");
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(et3.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+ // [base=der][]*[base=Mann]
+ String et4 =
+ "{@type=korap:group, relation=distance, @subtype=incl, constraint=[" +
+ "{@type=korap:distance, measure=w, direction=plus, min=0, max=INF}" +
+ "], " +
+ "operands=[" +
+ "{@type=korap:token, @value={@type=korap:term, @value=base:der, relation==}}," +
+ "{@type=korap:token, @value={@type=korap:term, @value=base:Mann, relation==}}" +
+ "]}";
+ ppt = new PoliqarpPlusTree("[base=der][]*[base=Mann]");
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(et4.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+ // startswith(<s>, [][base=Mann]
+ String et5 =
+ "{@type=korap:group, relation=position, position=startswith, @subtype=incl, operands=[" +
+ "{@type=korap:token, @value={@type=korap:elem, @value=s}," +
+ "{@type=korap:sequence, offset=1, operands=[" +
+ "{@type=korap:token, @value={@type=korap:term, @value=base:Mann, relation==}}" +
+ "]}" +
+ "]}";
+ ppt = new PoliqarpPlusTree("startswith(<s>, [][base=Mann]");
+ map = ppt.getRequestMap().get("query").toString();
+ assertEquals(et5.replaceAll(" ", ""), map.replaceAll(" ", ""));
+
+
+ }
@Test
public void testCoordinatedFields() throws QueryException {