X-Git-Url: http://jsfdemo.indexdata.com/?a=blobdiff_plain;f=src%2Forg%2Fz3950%2Fzing%2Fcql%2FCQLProxNode.java;h=9c7dff9ba9b7d953bfcdb50064fc5315dfd87c99;hb=f3c88fe15ee06a671407a0368e449db991526802;hp=1b9abe9ce3e1a04db0382e6a22ae04469dd4199a;hpb=f8154c71944186a9b64ddb782082a2026c5a912f;p=cql-java-moved-to-github.git diff --git a/src/org/z3950/zing/cql/CQLProxNode.java b/src/org/z3950/zing/cql/CQLProxNode.java index 1b9abe9..9c7dff9 100644 --- a/src/org/z3950/zing/cql/CQLProxNode.java +++ b/src/org/z3950/zing/cql/CQLProxNode.java @@ -1,37 +1,182 @@ -// $Id: CQLProxNode.java,v 1.1 2002-10-31 22:22:01 mike Exp $ +// $Id: CQLProxNode.java,v 1.7 2002-12-05 17:14:52 mike Exp $ package org.z3950.zing.cql; +import java.util.Vector; /** * Represents a proximity node in a CQL parse-tree. - * ## + * The left- and right-hand-sides must be satisfied by parts of the + * candidate records which are sufficiently close to each other, as + * specified by a set of proximity parameters. * - * @version $Id: CQLProxNode.java,v 1.1 2002-10-31 22:22:01 mike Exp $ + * @version $Id: CQLProxNode.java,v 1.7 2002-12-05 17:14:52 mike Exp $ */ public class CQLProxNode extends CQLBooleanNode { ModifierSet ms; + /** + * Creates a new, incomplete, proximity node with the + * specified left-hand side. No right-hand side is specified at + * this stage: that must be specified later, using the + * addSecondSubterm() method. (That may seem odd, but + * it's just easier to write the parser that way.) + *

+ * Proximity paramaters may be added at any time, before or after + * the right-hand-side sub-tree is added. + */ public CQLProxNode(CQLNode left) { ms = new ModifierSet("prox"); this.left = left; // this.right left unresolved for now ... } - // ... delayed "second half" of the constructor + /** + * Sets the right-hand side of the proximity node whose + * left-hand-side was specified at creation time. + */ public void addSecondSubterm(CQLNode right) { this.right = right; } + /** + * Adds a modifier of the specified type and + * value to a proximity node. Valid types are + * relation, distance, unit and + * ordering. + *

+ * For information on the semantics of these paramaters, see + * section 3.1 (Proximity) of + * A Gentle Introduction to CQL. + */ + public void addModifier(String type, String value) { + ms.addModifier(type, value); + } + + /** + * Returns an array of the modifiers associated with a proximity + * node. + * @return + * An array of modifiers, each represented by a two-element + * Vector, in which element 0 is the modifier type + * (e.g. distance or ordering) and element 1 is + * the associated value (e.g. 3 or unordered). + */ + public Vector[] getModifiers() { + return ms.getModifiers(); + } + String op() { return ms.toCQL(); } - public void addModifier(String type, String value) { - ms.addModifier(type, value); + String opXCQL(int level) { + return ms.toXCQL(level, "boolean"); } - String booleanXQL(int level) { - return ms.toXCQL(level, "boolean"); + /* + * proximity ::= exclusion distance ordered relation which-code unit-code. + * exclusion ::= '1' | '0' | 'void'. + * distance ::= integer. + * ordered ::= '1' | '0'. + * relation ::= integer. + * which-code ::= 'known' | 'private' | integer. + * unit-code ::= integer. + */ + String opPQF() { + int relCode = getRelCode(); + int unitCode = getProxUnitCode(); + + String res = "prox " + + "0 " + + ms.modifier("distance") + " " + + (ms.modifier("ordering").equals("ordered") ? 1 : 0) + " " + + relCode + " " + + "1 " + + unitCode; + + return res; + } + + private int getRelCode() { + String rel = ms.modifier("relation"); + if (rel.equals("<")) { + return 1; + } else if (rel.equals("<=")) { + return 2; + } else if (rel.equals("=")) { + return 3; + } else if (rel.equals(">=")) { + return 4; + } else if (rel.equals(">")) { + return 5; + } else if (rel.equals("<>")) { + return 6; + } + return 0; + } + + private int getProxUnitCode() { + String unit = ms.modifier("unit"); + if (unit.equals("word")) { + return 2; + } else if (unit.equals("sentence")) { + return 3; + } else if (unit.equals("paragraph")) { + return 4; + } else if (unit.equals("element")) { + return 8; + } + return 0; + } + + + byte[] opType1() { + byte[] op = new byte[100]; + int offset, value; + offset = putTag(CONTEXT, 46, CONSTRUCTED, op, 0); // Operator + op[offset++] = (byte)(0x80&0xff); // indefinite length + + offset = putTag(CONTEXT, 3, CONSTRUCTED, op, offset); // prox + op[offset++] = (byte)(0x80&0xff); // indefinite length + + offset = putTag(CONTEXT, 1, PRIMITIVE, op, offset); // exclusion + value = 0; // false + offset = putLen(numLen(value), op, offset); + offset = putNum(value, op, offset); + + offset = putTag(CONTEXT, 2, PRIMITIVE, op, offset); // distance + value = Integer.parseInt(ms.modifier("distance")); + offset = putLen(numLen(value), op, offset); + offset = putNum(value, op, offset); + + offset = putTag(CONTEXT, 3, PRIMITIVE, op, offset); // ordered + value = ms.modifier("ordering").equals("ordered") ? 1 : 0; + offset = putLen(numLen(value), op, offset); + offset = putNum(value, op, offset); + + offset = putTag(CONTEXT, 4, PRIMITIVE, op, offset); // relationType + value = getRelCode(); + offset = putLen(numLen(value), op, offset); + offset = putNum(value, op, offset); + + offset = putTag(CONTEXT, 5, CONSTRUCTED, op, offset); // proximityUnitCode + op[offset++] = (byte)(0x80&0xff); // indefinite length + offset = putTag(CONTEXT, 1, PRIMITIVE, op, offset); // known + value = getProxUnitCode(); + offset = putLen(numLen(value), op, offset); + offset = putNum(value, op, offset); + op[offset++] = 0x00; // end of proximityUnitCode + op[offset++] = 0x00; + + op[offset++] = 0x00; // end of prox + op[offset++] = 0x00; + op[offset++] = 0x00; // end of Operator + op[offset++] = 0x00; + + byte[] o = new byte[offset]; + System.arraycopy(op, 0, o, 0, offset); + return o; } }