以文本方式查看主题

-  中文XML论坛 - 专业的XML技术讨论区  (http://bbs.xml.org.cn/index.asp)
--  『 Semantic Web(语义Web)/描述逻辑/本体 』  (http://bbs.xml.org.cn/list.asp?boardid=2)
----  owl2prefuse如何遍历本体实例?  (http://bbs.xml.org.cn/dispbbs.asp?boardid=2&rootid=&id=75385)


--  作者:yfhbwh
--  发布时间:6/15/2009 9:24:00 AM

--  owl2prefuse如何遍历本体实例?
Animals本体:
<?xml version="1.0"?>
<rdf:RDF
    xmlns="http://localhost/Animals.owl#"
    xmlns:rdf="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
    xmlns:xsd="http://www.w3.org/2001/XMLSchema#"
    xmlns:rdfs="http://www.w3.org/2000/01/rdf-schema#"
    xmlns:owl="http://www.w3.org/2002/07/owl#"
  xml:base="http://localhost/Animals.owl">
  <owl:Ontology rdf:about=""/>
  <owl:Class rdf:about="#Animals">
      <rdfs:label rdf:datatype="http://www.w3.org/2001/XMLSchema#string"
      >动物</rdfs:label>
  </owl:Class>
  <owl:Class rdf:ID="Herbivores">
    <rdfs:subClassOf>
      <owl:Class rdf:ID="Animals"/>
    </rdfs:subClassOf>
    <rdfs:label rdf:datatype="http://www.w3.org/2001/XMLSchema#string"
    >食草动物</rdfs:label>
  </owl:Class>
  <owl:Class rdf:ID="Predators">
    <rdfs:subClassOf>
      <owl:Class rdf:ID="Animals"/>
    </rdfs:subClassOf>
    <rdfs:label rdf:datatype="http://www.w3.org/2001/XMLSchema#string"
    >食肉动物</rdfs:label>
  </owl:Class>
  <owl:DatatypeProperty rdf:ID="age">
    <rdfs:label rdf:datatype="http://www.w3.org/2001/XMLSchema#string"
    >年龄</rdfs:label>
    <rdfs:domain rdf:resource="#Animals"/>
    <rdfs:range rdf:resource="http://www.w3.org/2001/XMLSchema#int"/>
  </owl:DatatypeProperty>
  <owl:DatatypeProperty rdf:ID="weight">
    <rdfs:label rdf:datatype="http://www.w3.org/2001/XMLSchema#string"
    >重量</rdfs:label>
    <rdfs:domain rdf:resource="#Animals"/>
    <rdfs:range rdf:resource="http://www.w3.org/2001/XMLSchema#int"/>
  </owl:DatatypeProperty>
  <Predators rdf:ID="_00001">
    <rdfs:label rdf:datatype="http://www.w3.org/2001/XMLSchema#string"
    >狮子</rdfs:label>
    <age rdf:datatype="http://www.w3.org/2001/XMLSchema#int"
    >10</age>
    <weight rdf:datatype="http://www.w3.org/2001/XMLSchema#int"
    >500</weight>
  </Predators>
</rdf:RDF>

converter类读取本体文件
public class Converter
{
 protected OntModel m_model;
 
 public Converter(String p_OWLFile)
 {
  load(p_OWLFile);
 }
 
 private void load(String p_OWLFile)
 {
  m_model = ModelFactory.createOntologyModel(OntModelSpec.OWL_MEM);
  
  InputStream in = FileManager.get().open(p_OWLFile);
  
  if(in == null)
  {
   throw new IllegalArgumentException("File: " + p_OWLFile + "not found!");
  }
  
  m_model.read(in, "");
 }
}

OWLGraphConverter画图
public class OWLGraphConverter extends Converter
{
    /**
     * The created Prefuse graph.
     */
    private Graph m_graph;
    
    /**
     * An ArrayList containing all the edges that have to be added to the Prefuse
     * graph.
     */
    private ArrayList<String[]> m_edges;
    
    /**
     * An Hashtable containing all the nodes in Prefuse graph.
     */
    private Hashtable<String, Node> m_nodes;
    
    /**
     * An ArrayList containing the URI's of OWL classes that should not be converted
     * into the Prefuse graph.
     */
    private ArrayList<String> m_uselessType;
    
    
    /**
     * Creates a new instance of OWLGraphConverter
     * @param p_OWLFile The path to the OWL file that needs to be converted.
     * @param p_directed A boolean indicating whether the Prefuse graph needs to
     * be directed.
     */
    public OWLGraphConverter(String p_OWLFile, boolean p_directed)
    {
        super(p_OWLFile);
        init(p_directed);
    }
    
    /**
     * Initialize the graph converter.
     * @param p_directed A boolean indicating whether the Prefuse graph needs to
     * be directed.
     */
    private void init(boolean p_directed)
    {
        m_edges = new ArrayList<String[]>();
        m_nodes = new Hashtable<String, Node>();
        
        // Create an ArrayList which contains URI's of nodes we do not want to
        // visualize, because they are to general.
        m_uselessType = new ArrayList<String>();
        m_uselessType.add("http://www.w3.org/2002/07/owl#Class");
        m_uselessType.add("http://www.w3.org/2000/01/rdf-schema#Class");
        
        // Create the graph.
        createGraph(p_directed);
    }
    
    /**
     * Return the created Prefuse graph.
     * @return The created Prefuse graph.
     */
    public Graph getGraph()
    {
        return m_graph;
    }
    
    /**
     * Create the Prefuse graph. This method creates an empty graph and adds the
     * appropriate columns to the node- and edgestable. After that it gets the root
     * class (owl:Thing) of the OWL graph and recursively starts building the graph
     * from there.
     * This method is automatically called from the constructors of this converter.
     * @param p_directed A boolean indicating whether the Prefuse graph needs to
     * be directed.
     */
    private void createGraph(boolean p_directed)
    {
        // Create a new empty graph.
        m_graph = new Graph(p_directed);
        
        // Add the appropriate columns.
        m_graph.getNodeTable().addColumn("URI", String.class);
        m_graph.getNodeTable().addColumn("name", String.class);
        m_graph.getNodeTable().addColumn("type", String.class);
        m_graph.getEdgeTable().addColumn("label", String.class);
        
        // Get the root node.
        OntClass rootClass = m_model.getOntClass("http://localhost/Animals.owl#Animals");
        // Build the entire tree.
        buildGraph(rootClass);
        
        // All the edges are stored in an ArrayList, because they can only be added
        // if all the appropriate nodes exist. At this point this is the case, so
        // all the nodes are created.
        createEdges();
    }
    
    /**
     * Build the Prefuse graph, this method is called recursively.
     * @param p_currentClass The class which is being added to the graph.
     */
    private void buildGraph(OntClass p_currentClass)
    {
        // If there is no root node yet, one is created.
        Node currNode = m_graph.addNode();
        currNode.setString("URI", p_currentClass.getURI());
        currNode.setString("name", p_currentClass.getLocalName());
        currNode.setString("type", "class");
        
        // Walk trough the subclasses of the current class.
        ExtendedIterator itClasses = p_currentClass.listSubClasses(true);
        while(itClasses.hasNext())
        {
             //Recurse trough the subclasses of the current node.
            buildGraph((OntClass) itClasses.next());
        }
        
        // Walk trough the instances of the current class.
        ExtendedIterator itIndividuals = p_currentClass.listInstances();
        while(itIndividuals.hasNext())
        {
            Individual foundIndividual = (Individual) itIndividuals.next();
            if (foundIndividual.getURI() != null)
            {
                // Create the node for this instance.
                Node node = m_graph.addNode();
                node.setString("URI", foundIndividual.getURI());
                node.setString("name", foundIndividual.getLocalName());
                node.setString("type", "individual");
            
                // Add this node to the nodes ArrayList.
                m_nodes.put(foundIndividual.getURI(), node);

                // Add the edges, connected to this node, to the edges ArrayList.
                storeEdges(foundIndividual);
            }
        }
        
        // Add this node to the nodes ArrayList.
        m_nodes.put(p_currentClass.getURI(), currNode);
        
        // Add the edges, connected to this node, to the edges ArrayList.
        storeEdges(p_currentClass);
    }
    
    /**
     * Temporarily store the edges which need to be added the graph. All the edges
     * are stored in an ArrayList, because they can only be added if all the
     * appropriate nodes exist. At this point this is the case, so all the nodes
     * are created.
     * @param p_resource The Jena OntResource of which the edges need to be stored.
     */
    private void storeEdges(OntResource p_resource)
    {
        String sourceURI = p_resource.getURI();
        
        if (!m_uselessType.contains(sourceURI))
        {
            StmtIterator itProperties = p_resource.listProperties();
            while (itProperties.hasNext())
            {
                Statement property = itProperties.nextStatement();
                String localName = property.getPredicate().getLocalName();

                if (property.getObject().isResource())
                {
                    String targetURI = ((Resource) property.getObject()).getURI();
                    if (!m_uselessType.contains(targetURI) && targetURI != null)
                    {
                        String[] edge = new String[3];
                        edge[0] = sourceURI;
                        edge[1] = localName;
                        edge[2] = targetURI;
                        m_edges.add(edge);
                    }
                }
            }
        }
    }
    
    /**
     * Create edges for the relevant properties of the resource.
     */
    private void createEdges()
    {
        for (int i = 0; i < m_edges.size(); i++)
        {
            String[] strEdge = m_edges.get(i);
            
            // Get the source and the target node.
            Node source = m_nodes.get(strEdge[0]);
            Node target = m_nodes.get(strEdge[2]);
            
            Edge edge = m_graph.addEdge(source, target);
            edge.setString("label", strEdge[1]);
        }
    }
}

最后由主程序调用

OWLGraphConverter类实际上就是一个递归运算,遍历本体的所有类和实例,而根目录就是:
OntClass rootClass = m_model.getOntClass("http://localhost/Animals.owl#Animals");

问题是我把这句改成:
Individual individual = m_model.getIndividual("http://localhost/Animals.owl#_00001");
删掉显示类的语句,只显示以_00001实例为根目录的所有属性,报空指针错:
Exception in thread "main" java.lang.NullPointerException
 at owl2prefuse.graph.OWLGraphConverter.buildGraph(OWLGraphConverter.java:127)
 at owl2prefuse.graph.OWLGraphConverter.createGraph(OWLGraphConverter.java:111)
 at owl2prefuse.graph.OWLGraphConverter.init(OWLGraphConverter.java:76)
 at owl2prefuse.graph.OWLGraphConverter.<init>(OWLGraphConverter.java:55)
 at Demo.<init>(Demo.java:30)
 at Demo.main(Demo.java:50)

不知道为什么,急啊,望各位高手不吝赐教啊!!!


--  作者:iamwym
--  发布时间:6/15/2009 11:14:00 AM

--  
你搞了好像太复杂了吧,用个树就可以了,不一定需要用图
--  作者:yfhbwh
--  发布时间:6/15/2009 7:02:00 PM

--  
我也想用树啊
可是导师说了要用图表示
我也没办法啊
W 3 C h i n a ( since 2003 ) 旗 下 站 点
苏ICP备05006046号《全国人大常委会关于维护互联网安全的决定》《计算机信息网络国际联网安全保护管理办法》
109.375ms