neilg 2002/08/13 15:32:44
Modified: java/src/org/apache/xerces/impl/xs XMLSchemaValidator.java
java/src/org/apache/xerces/impl/xs/identity Field.java
Selector.java XPathMatcher.java
Log:
more identity constraint performance fixes. Eliminated unnecessary
endDocumentFragment calls for XPathMatchers.
Selectors now do not attempt to examine character data; only fields need do this.
Refactored some code and eliminated some unnecessary global variables from
XPathMatcher.
Revision Changes Path
1.79 +1 -5
xml-xerces/java/src/org/apache/xerces/impl/xs/XMLSchemaValidator.java
Index: XMLSchemaValidator.java
===================================================================
RCS file:
/home/cvs/xml-xerces/java/src/org/apache/xerces/impl/xs/XMLSchemaValidator.java,v
retrieving revision 1.78
retrieving revision 1.79
diff -u -r1.78 -r1.79
--- XMLSchemaValidator.java 12 Aug 2002 18:12:24 -0000 1.78
+++ XMLSchemaValidator.java 13 Aug 2002 22:32:44 -0000 1.79
@@ -2090,11 +2090,8 @@
XPathMatcher matcher = fMatcherStack.getMatcherAt(i);
IdentityConstraint id;
if ((id = matcher.getIDConstraint()) != null && id.getCategory() !=
IdentityConstraint.IC_KEYREF) {
- matcher.endDocumentFragment();
fValueStoreCache.transplant(id);
}
- else if (id == null)
- matcher.endDocumentFragment();
}
// now handle keyref's/...
for (int i = oldCount - 1; i >= newCount; i--) {
@@ -2104,7 +2101,6 @@
ValueStoreBase values = fValueStoreCache.getValueStoreFor(id);
if (values != null) // nothing to do if nothing matched!
values.endDocumentFragment();
- matcher.endDocumentFragment();
}
}
fValueStoreCache.endElement();
1.4 +2 -2
xml-xerces/java/src/org/apache/xerces/impl/xs/identity/Field.java
Index: Field.java
===================================================================
RCS file:
/home/cvs/xml-xerces/java/src/org/apache/xerces/impl/xs/identity/Field.java,v
retrieving revision 1.3
retrieving revision 1.4
diff -u -r1.3 -r1.4
--- Field.java 29 Jan 2002 01:15:15 -0000 1.3
+++ Field.java 13 Aug 2002 22:32:44 -0000 1.4
@@ -197,7 +197,7 @@
/** Constructs a field matcher. */
public Matcher(Field.XPath xpath, ValueStore store) {
- super(xpath, true, null);
+ super(xpath, null);
fStore = store;
} // <init>(Field.XPath,ValueStore)
1.6 +14 -6
xml-xerces/java/src/org/apache/xerces/impl/xs/identity/Selector.java
Index: Selector.java
===================================================================
RCS file:
/home/cvs/xml-xerces/java/src/org/apache/xerces/impl/xs/identity/Selector.java,v
retrieving revision 1.5
retrieving revision 1.6
diff -u -r1.5 -r1.6
--- Selector.java 12 Aug 2002 18:12:24 -0000 1.5
+++ Selector.java 13 Aug 2002 22:32:44 -0000 1.6
@@ -64,9 +64,9 @@
import org.apache.xerces.xni.XNIException;
import org.apache.xerces.xni.XMLAttributes;
import org.apache.xerces.xni.psvi.ElementPSVI;
-import org.apache.xerces.util.SymbolTable;
import org.apache.xerces.impl.xs.XSElementDecl;
import org.apache.xerces.impl.xs.XSAttributeGroupDecl;
+import org.apache.xerces.util.SymbolTable;
import org.xml.sax.SAXException;
@@ -198,7 +198,7 @@
/** Constructs a selector matcher. */
public Matcher(Selector.XPath xpath, FieldActivator activator) {
- super(xpath, false, Selector.this.fIdentityConstraint);
+ super(xpath, Selector.this.fIdentityConstraint);
fFieldActivator = activator;
} // <init>(Selector.XPath,FieldActivator)
@@ -209,10 +209,9 @@
public void startDocumentFragment(SymbolTable symbolTable)
throws XNIException {
super.startDocumentFragment(symbolTable);
- //super.startDocumentFragment(context, symbolTable);
fElementDepth = 0;
fMatchedDepth = -1;
- } // startDocumentFragment(SymbolTable)
+ } // startDocumentFragment()
/**
* The start of an element. If the document specifies the start element
@@ -251,6 +250,15 @@
fFieldActivator.endValueScopeFor(fIdentityConstraint);
}
}
+
+ //
+ // Protected methods
+ //
+
+ // overridden to do nothing; selectors don't care
+ // about element content
+ protected void handleContent(XSElementDecl eDecl, ElementPSVI ePSVI) {
+ } // handleContent(XSElementDecl, ElementPSVI)
} // class Matcher
1.8 +73 -99
xml-xerces/java/src/org/apache/xerces/impl/xs/identity/XPathMatcher.java
Index: XPathMatcher.java
===================================================================
RCS file:
/home/cvs/xml-xerces/java/src/org/apache/xerces/impl/xs/identity/XPathMatcher.java,v
retrieving revision 1.7
retrieving revision 1.8
diff -u -r1.7 -r1.8
--- XPathMatcher.java 12 Aug 2002 18:12:24 -0000 1.7
+++ XPathMatcher.java 13 Aug 2002 22:32:44 -0000 1.8
@@ -116,6 +116,12 @@
DEBUG_MATCH ||
DEBUG_STACK;
+ // constants describing whether a match was made,
+ // and if so how.
+ protected static final int MATCHED = 1;
+ protected static final int MATCHED_ATTRIBUTE = 3;
+ protected static final int MATCHED_DESCENDANT = 5;
+
//
// Data
//
@@ -123,17 +129,8 @@
/** XPath location path. */
private XPath.LocationPath[] fLocationPaths;
- /** Application preference to buffer content or not. */
- private boolean fShouldBufferContent;
-
- /** True if should buffer character content <em>at this time</em>. */
- private boolean fBufferContent;
-
- /** Buffer to hold match text. */
- private StringBuffer fMatchedBuffer = new StringBuffer();
-
/** True if XPath has been matched. */
- private boolean[] fMatched;
+ private int[] fMatched;
/** The matching string. */
private String fMatchedString;
@@ -150,20 +147,13 @@
*/
private int [] fNoMatchDepth;
- // Xerces 1.x framework
-
- /** Symbol table. */
- protected SymbolTable fSymbolTable;
-
- /** Namespace scope. */
- /*** REVISIT: do we need this? -NG
- protected NamespaceContext fNamespacesScope;
- */
-
// the Identity constraint we're the matcher for. Only
// used for selectors!
protected IdentityConstraint fIDConstraint;
+ // the symbolTable for the XPath parser
+ protected SymbolTable fSymbolTable;
+
//
// Constructors
//
@@ -175,7 +165,7 @@
* @param xpath The xpath.
*/
public XPathMatcher(XPath xpath) {
- this(xpath, false, null);
+ this(xpath, null);
} // <init>(XPath)
/**
@@ -188,15 +178,14 @@
* @param idConstraint: the identity constraint we're matching for;
* null unless it's a Selector.
*/
- public XPathMatcher(XPath xpath, boolean shouldBufferContent,
IdentityConstraint idConstraint) {
+ public XPathMatcher(XPath xpath, IdentityConstraint idConstraint) {
fLocationPaths = xpath.getLocationPaths();
- fShouldBufferContent = shouldBufferContent;
fIDConstraint = idConstraint;
fStepIndexes = new IntStack[fLocationPaths.length];
for(int i=0; i<fStepIndexes.length; i++) fStepIndexes[i] = new IntStack();
fCurrentStep = new int[fLocationPaths.length];
fNoMatchDepth = new int[fLocationPaths.length];
- fMatched = new boolean[fLocationPaths.length];
+ fMatched = new int[fLocationPaths.length];
if (DEBUG_METHODS) {
System.out.println(toString()+"#<init>()");
}
@@ -210,7 +199,7 @@
public boolean isMatched() {
// xpath has been matched if any one of the members of the union have
matched.
for (int i=0; i < fLocationPaths.length; i++)
- if (fMatched[i]) return true;
+ if ((fMatched[i] & MATCHED) == MATCHED) return true;
return false;
} // isMatched():boolean
@@ -233,6 +222,31 @@
// Protected methods
//
+ protected void handleContent(XSElementDecl eDecl, ElementPSVI ePSVI) {
+ fMatchedString = ePSVI.getSchemaNormalizedValue();
+ // REVISIT: make sure type is simple!
+ XSSimpleType val=null;
+
+ if (eDecl!=null) {
+ XSTypeDecl type = eDecl.fType;
+ if (type != null) {
+ if (type.getTypeCategory() == XSTypeDecl.COMPLEX_TYPE) {
+ XSComplexTypeDecl ctype = (XSComplexTypeDecl)type;
+ val = (XSSimpleType)ctype.getSimpleType();
+ }
+ else {
+ val = (XSSimpleType)(type);
+ }
+ }
+ }
+
+ if(eDecl != null) {
+ matched(fMatchedString, val, (eDecl.getIsNillable()));
+ } else {
+ matched(fMatchedString, val, false);
+ }
+ } // handleContent(XSElementDecl, ElementPSVI)
+
/**
* This method is called when the XPath handler matches the
* XPath expression. Subclasses can override this method to
@@ -265,17 +279,17 @@
}
// reset state
- clear();
+ fSymbolTable = symbolTable;
+ fMatchedString = null;
for(int i = 0; i < fLocationPaths.length; i++) {
fStepIndexes[i].clear();
fCurrentStep[i] = 0;
fNoMatchDepth[i] = 0;
+ fMatched[i] = 0;
}
- // keep values
- fSymbolTable = symbolTable;
- } // startDocumentFragment(NamespaceContext)
+ } // startDocumentFragment(SymbolTable)
/**
* The start of an element. If the document specifies the start element
@@ -304,7 +318,7 @@
fStepIndexes[i].push(startStep);
// try next xpath, if not matching
- if (fMatched[i] || fNoMatchDepth[i] > 0) {
+ if ((fMatched[i] & MATCHED) == MATCHED || fNoMatchDepth[i] > 0) {
fNoMatchDepth[i]++;
continue;
}
@@ -327,11 +341,7 @@
if (DEBUG_MATCH) {
System.out.println(toString()+" XPath MATCHED!");
}
- fMatched[i] = true;
- int j=0;
- for(; j<i && !fMatched[j]; j++);
- if(j==i)
- fBufferContent = fShouldBufferContent;
+ fMatched[i] = MATCHED;
continue;
}
@@ -347,6 +357,7 @@
}
fCurrentStep[i]++;
}
+ boolean sawDescendant = fCurrentStep[i] > descendantStep;
if (fCurrentStep[i] == steps.length) {
if (DEBUG_MATCH) {
System.out.println(toString()+" XPath DIDN'T MATCH!");
@@ -385,11 +396,11 @@
}
}
if (fCurrentStep[i] == steps.length) {
- fMatched[i] = true;
- int j=0;
- for(; j<i && !fMatched[j]; j++);
- if(j==i)
- fBufferContent = fShouldBufferContent;
+ if(sawDescendant) {
+ fMatched[i] = MATCHED_DESCENDANT;
+ } else {
+ fMatched[i] = MATCHED;
+ }
continue;
}
@@ -418,21 +429,20 @@
}
}
- for (int aindex = 0; aindex < attrCount; aindex++) {
- attributes.getName(aindex, aname);
+ for (int aIndex = 0; aIndex < attrCount; aIndex++) {
+ attributes.getName(aIndex, aname);
if (nodeTest.type != XPath.NodeTest.QNAME ||
nodeTest.name.equals(aname)) {
fCurrentStep[i]++;
if (fCurrentStep[i] == steps.length) {
- fMatched[i] = true;
+ fMatched[i] = MATCHED_ATTRIBUTE;
int j=0;
- for(; j<i && !fMatched[j]; j++);
+ for(; j<i && ((fMatched[j] & MATCHED) != MATCHED);
j++);
if(j==i) {
- String avalue = attributes.getValue(aindex);
+ String avalue = attributes.getValue(aIndex);
fMatchedString = avalue;
- // now, we have to go on the hunt for
- // datatype validator; not an easy or pleasant
task...
+ // find Datatype validator...
XSSimpleType aValidator = null;
if (attrGrp != null) {
XSAttributeUseImpl tempAttUse =
attrGrp.getAttributeUse(aname.uri, aname.localpart);
@@ -448,7 +458,7 @@
}
}
}
- if (!fMatched[i]) {
+ if ((fMatched[i] & MATCHED) != MATCHED) {
if(fCurrentStep[i] > descendantStep) {
fCurrentStep[i] = descendantStep;
continue;
@@ -472,6 +482,7 @@
*
* @param element The name of the element.
* @param eDecl: the element declaration
+ * @param ePSVI contains validation info for this element
*
* @throws SAXException Thrown by handler to signal an error.
*/
@@ -483,6 +494,9 @@
")");
}
for(int i = 0; i<fLocationPaths.length; i++) {
+ // go back a step
+ fCurrentStep[i] = fStepIndexes[i].pop();
+
// don't do anything, if not matching
if (fNoMatchDepth[i] > 0) {
fNoMatchDepth[i]--;
@@ -491,39 +505,19 @@
// signal match, if appropriate
else {
int j=0;
- for(; j<i && !fMatched[j]; j++);
- if (j<i) continue;
- if (fBufferContent) {
- fBufferContent = false;
- fMatchedString = ePSVI.getSchemaNormalizedValue();
- // REVISIT: make sure type is simple!
- XSSimpleType val=null;
-
- if (eDecl!=null) {
- XSTypeDecl type = eDecl.fType;
- if (type != null) {
- if (type.getTypeCategory() == XSTypeDecl.COMPLEX_TYPE) {
- XSComplexTypeDecl ctype = (XSComplexTypeDecl)type;
- val = (XSSimpleType)ctype.getSimpleType();
- }
- else {
- val = (XSSimpleType)(type);
- }
- }
- }
-
- if(eDecl != null) {
- matched(fMatchedString, val, (eDecl.getIsNillable()));
- } else
- matched(fMatchedString, val, false);
-
+ for(; j<i && ((fMatched[j] & MATCHED) != MATCHED); j++);
+ if ((j<i) || (fMatched[j] == 0) ||
+ ((fMatched[j] & MATCHED_ATTRIBUTE) == MATCHED_ATTRIBUTE)) {
+ continue;
}
- clear();
+ // only certain kinds of matchers actually
+ // match element content. This permits
+ // them a way to override this to do nothing
+ // and hopefully save a few operations.
+ handleContent(eDecl, ePSVI);
+ fMatched[i] = 0;
}
- // go back a step
- fCurrentStep[i] = fStepIndexes[i].pop();
-
if (DEBUG_STACK) {
System.out.println(toString()+": "+fStepIndexes[i]);
}
@@ -531,17 +525,6 @@
} // endElement(QName)
- /**
- * The end of the document fragment.
- *
- * @throws SAXException Thrown by handler to signal an error.
- */
- public void endDocumentFragment() throws XNIException {
- if (DEBUG_METHODS) {
- System.out.println(toString()+"#endDocumentFragment()");
- }
- } // endDocumentFragment()
-
//
// Object methods
//
@@ -582,15 +565,6 @@
//
// Private methods
//
-
- /** Clears the match values. */
- private void clear() {
- fBufferContent = false;
- fMatchedBuffer.setLength(0);
- fMatchedString = null;
- for(int i = 0; i < fLocationPaths.length; i++)
- fMatched[i] = false;
- } // clear()
/** Normalizes text. */
private String normalize(String s) {
---------------------------------------------------------------------
To unsubscribe, e-mail: [EMAIL PROTECTED]
For additional commands, e-mail: [EMAIL PROTECTED]