Laboratorium XML
wtorek 11.00—12.30
»Home
»Materiały
  »DTD & co.
  »SAX
  »DOM
  »Zadanie 2
  »XPath
  »XSLT
  »Simple
  »JDOM
  »JS
»Odnośniki
  »Xerces2
»Zadania

Xerces2 na mancie

W shellu lub w ~/.bash_profile

export CLASSPATH=/usr/share/java2/xercesImpl.jar:/usr/share/java2/xml-apis.jar:.

Rzeczywiście mam nowszą wersję biblioteki Xerces1 niż jest na mancie:

## @psi
$ java -classpath /usr/share/java/xerces.jar org.apache.xerces.framework.Version
Xerces 1.4.4
## @manta
$ java -classpath /usr/share/java/xerces.jar org.apache.xerces.framework.Version
Xerces 1.2.3

Ale te same wersje Xerces 2

## @psi
$ java -classpath /usr/share/java/xercesImpl.jar org.apache.xerces.impl.Version
Xerces-J 2.6.2
## @manta
$ java -classpath /usr/share/java2/xercesImpl.jar org.apache.xerces.impl.Version
Xerces-J 2.6.2

Przykład

Program dodający do drzewa czytanego ze standardowego wejścia liczby podane w argumentach przy zachowaniu sortowania i wypisujący rozszerzone drzewo na standardowe wyjście.

Dla przykładowego wywołania

$ echo '<!DOCTYPE root SYSTEM "sorted-tree.dtd">' \
       ' <root value="15" xmlns="http://example.com/sorted-tree"/>' \
     | java SortedTreeExpander 12 7 13 14 7 \
     | java SortedTreeExpander 19 7

uzyskujemy na standardowym wyjściu dokument

<?xml version="1.0" encoding="utf-8"?>
<!DOCTYPE root SYSTEM "sorted-tree.dtd">
<root value="15" xmlns="http://example.com/sorted-tree">
    <left value="12">
        <left count="3" value="7"/>
        <right value="13">
            <right value="14"/>
        </right>
    </left>
    <right value="19"/>
</root>

opisany schematem sorted-tree.xsd:

<xsd:schema xmlns:xsd="http://www.w3.org/2001/XMLSchema"
            xmlns="http://example.com/sorted-tree"
            targetNamespace="http://example.com/sorted-tree">
  <!-- xmlns="" aby odwoływać się do nazw typów -->

<xsd:element name="root" type="Node"/>
<xsd:element name="left" type="Node"/>
<xsd:element name="right" type="Node"/>

<xsd:complexType name="Node">
  <xsd:sequence>
    <xsd:element ref="left" minOccurs="0"/>
    <xsd:element ref="right" minOccurs="0"/>
  </xsd:sequence>
  <xsd:attribute name="value" type="xsd:integer"/>
  <xsd:attribute name="count" type="xsd:integer" default="1"/>
</xsd:complexType>

</xsd:schema>

oraz sorted-tree.dtd:

<!ELEMENT root (left?,right?)>
<!ELEMENT left (left?,right?)>
<!ELEMENT right (left?,right?)>
<!ATTLIST root
          value NMTOKEN #REQUIRED
          count NMTOKEN #IMPLIED
          xmlns CDATA #IMPLIED>
<!ATTLIST left
          value NMTOKEN #REQUIRED
          count NMTOKEN #IMPLIED>
<!ATTLIST right value NMTOKEN #REQUIRED>
<!ATTLIST right
          value NMTOKEN #REQUIRED
          count NMTOKEN #IMPLIED>

Program ma postać pub/SortedTreeExpander.java:

import java.io.IOException;
import java.io.OutputStream;
import org.apache.xerces.parsers.DOMParser;
import org.apache.xml.serialize.OutputFormat;
import org.apache.xml.serialize.XMLSerializer;
import org.w3c.dom.*;
import org.xml.sax.InputSource;
import org.xml.sax.SAXParseException;
import org.xml.sax.helpers.DefaultHandler;


class SortedTreeExpander extends DefaultHandler
{
    public static void main(String args[]) throws Exception
    {
        SortedTreeExpander tree = null;

        try {
            tree = new SortedTreeExpander(new InputSource(System.in));
        } catch (SAXParseException e) {
            parse_error_message(e);
            System.exit(1);
        }
        for (int i = 0; i < args.length; i++) {
            tree.add(Integer.parseInt(args[i]));
        }
        tree.write(System.out);
    }

    Document document;

    public SortedTreeExpander(InputSource input) throws Exception
    {
        DOMParser parser = new DOMParser();
        parser.setFeature("http://xml.org/sax/features/validation", true);
        parser.setFeature("http://apache.org/xml/features/validation/schema", true);
        parser.setProperty(
            "http://apache.org/xml/properties/schema/external-schemaLocation",
            "http://example.com/sorted-tree " +
            (new java.io.File("sorted-tree.xsd")).getAbsolutePath());
        parser.setFeature(
            "http://apache.org/xml/features/dom/include-ignorable-whitespace", false);
        parser.setErrorHandler(this);
        parser.parse(input);
        document = parser.getDocument();
    }

    public void add(int value)
    {
        Element elem = document.getDocumentElement();
        while (true) {
            int v = Integer.parseInt(elem.getAttribute("value"));
            if (value < v) {
                Node child = elem.getFirstChild();
                if (child != null && child.getNodeType() == Node.ELEMENT_NODE &&
                    "left".equals(((Element) child).getTagName())) {
                    elem = (Element) child;
                } else {
                    Element new_elem = document.createElement("left");
                    new_elem.setAttribute("value", Integer.toString(value));
                    elem.insertBefore(new_elem, child);
                    return;
                }
            } else if (value > v) {
                Node child = elem.getLastChild();
                if (child != null && child.getNodeType() == Node.ELEMENT_NODE &&
                    "right".equals(((Element) child).getTagName())) {
                    elem = (Element) child;
                } else {
                    Element new_elem = document.createElement("right");
                    new_elem.setAttribute("value", Integer.toString(value));
                    elem.appendChild(new_elem);
                    return;
                }
            } else {
                String count = elem.getAttribute("count");
                if (count != "") {
                    elem.setAttribute("count",
                                      Integer.toString(Integer.parseInt(count) + 1));
                } else {
                    elem.setAttribute("count", "2");
                }
                return;
            }
        }
    }

    public void write(OutputStream out) throws IOException
    {
        XMLSerializer serializer =
            new XMLSerializer(out, new OutputFormat(document, "utf-8", true));
        serializer.serialize(document);
    }

    public static void parse_error_message(SAXParseException e) {
        System.err.println(e.getSystemId() + ":" +
                           e.getLineNumber() + ":" +
                           e.getColumnNumber() + ": " +
                           e.getMessage());
    }

    public void error(SAXParseException e)
    {
        parse_error_message(e);
        System.exit(1);
    }

    public void fatalError(SAXParseException e)
    {
        parse_error_message(e);
        System.exit(1);
    }
}

Zadanie 2