Github user jessehatfield commented on a diff in the pull request:

    https://github.com/apache/incubator-rya/pull/206#discussion_r134081316
  
    --- Diff: 
sail/src/main/java/org/apache/rya/rdftriplestore/inference/InferenceEngine.java 
---
    @@ -416,22 +425,131 @@ private void 
refreshHasValueRestrictions(Map<Resource, URI> restrictions) throws
             }
         }
     
    -    private static Vertex getVertex(Graph graph, Object id) {
    -        Iterator<Vertex> it = graph.vertices(id.toString());
    +    private void refreshIntersectionOf() throws QueryEvaluationException {
    +        final Map<Resource, List<Set<Resource>>> intersectionsProp = new 
HashMap<>();
    +
    +        // First query for all the owl:intersectionOf's.
    +        // If we have the following intersectionOf:
    +        // :A owl:intersectionOf[:B, :C]
    +        // It will be represented by triples following a pattern similar 
to:
    +        // <:A> owl:intersectionOf _:bnode1 .
    +        //  _:bnode1 rdf:first <:B> .
    +        //  _:bnode1 rdf:rest _:bnode2 .
    +        // _:bnode2 rdf:first <:C> .
    +        // _:bnode2 rdf:rest rdf:nil .
    +        ryaDaoQueryWrapper.queryAll(null, OWL.INTERSECTIONOF, null, new 
RyaDaoStatementIterHandler() {
    +            @Override
    +            public void handleStatementIter(final Statement st1) throws 
Exception {
    +                final Resource type = st1.getSubject();
    +                // head will point to a type that is part of the 
intersection.
    +                URI head = (URI) st1.getObject();
    +                if (!intersectionsProp.containsKey(type)) {
    +                    intersectionsProp.put(type, new 
ArrayList<Set<Resource>>());
    +                }
    +                final Set<Resource> intersection = new HashSet<>();
    +                // Go through and find all bnodes that are part of the 
defined
    +                // intersection.
    +                while (!RDF.NIL.equals(head)) {
    +                    // rdf.first will point to a type item that is in the
    +                    // intersection.
    +                    ryaDaoQueryWrapper.queryFirst(head, RDF.FIRST, null, 
new RyaDaoStatementIterHandler() {
    +                        @Override
    +                        public void handleStatementIter(final Statement 
st2) throws Exception{
    +                            // The object found in the query represents a 
type
    +                            // that should be included in the intersection.
    +                            final URI obj2 = (URI) st2.getObject();
    +                            intersection.add(obj2);
    +                        }
    +                    });
    +                    final List<URI> headHolder = new ArrayList<>(1);
    +                    // rdf.rest will point to the next bnode that's part 
of the
    +                    // intersection.
    +                    ryaDaoQueryWrapper.queryFirst(head, RDF.REST, null, 
new RyaDaoStatementIterHandler() {
    +                        @Override
    +                        public void handleStatementIter(final Statement 
st3) throws Exception {
    +                            // This object is the next bnode head to look 
for.
    +                            final URI obj3 = (URI) st3.getObject();
    +                            headHolder.add(obj3);
    +                        }
    +                    });
    +                    // As long as we get a new head there are more bnodes 
that
    +                    // are part of the intersection. Keep going until we 
reach
    +                    // rdf.nil.
    +                    if (!headHolder.isEmpty()) {
    +                        head = headHolder.get(0);
    +                    } else {
    +                        head = RDF.NIL;
    +                    }
    +                }
    +                // Add this intersection for this type. There may be more
    +                // intersections for this type so each type has a list of
    +                // intersection sets.
    +                intersectionsProp.get(type).add(intersection);
    +            }
    +        });
    +
    +        for (final Map.Entry<Resource, List<Set<Resource>>> entry : 
intersectionsProp.entrySet()) {
    +            final Resource type = entry.getKey();
    +            final List<Set<Resource>> intersectionList = entry.getValue();
    +            final Set<Resource> otherTypes = new HashSet<>();
    +            // Combine all of a type's intersections together.
    +            for (final Set<Resource> intersection : intersectionList) {
    +                otherTypes.addAll(intersection);
    +            }
    +            for (final Resource other : otherTypes) {
    +                // :A intersectionOf[:B, :C] implies that
    +                // :A subclassOf :B
    +                // :A subclassOf :C
    +                // So add each type that's part of the intersection to the
    +                // subClassOf graph.
    +                addSubClassOf(type, other);
    +                for (final Set<Resource> intersection : intersectionList) {
    +                    if (!intersection.contains(other)) {
    +                        addIntersection(intersection, other);
    --- End diff --
    
    I'm not sure if that's the same. I can read "A = (B and C)" two ways -- 
either "A is the intersection of B and C":
        <A> owl:intersectionOf (<B> <C>) .
        <D> owl:intersectionOf (<B> <C>) .
        <D> rdfs:subClassOf <E> .
    or "A is equivalent to some anonymous class which is the intersection of B 
and C:
        <A> owl:equivalentClass _:bnode
        _:bnode owl:intersectionOf (<B> <C>) .
        _:bnode owl:equivalentClass <D> .
        <D> rdfs:subClassOf <E> .
    
    In the latter case, we have A subClassOf E just from subclass and 
equivalent class transitivity, without touching the intersection.
    
    In the former, I suppose you could infer that A and D are equivalent 
classes by comparing their intersections. That would require comparing the 
actual contents of all intersection lists to find any pairs that contain the 
same set of classes. That might be something to do in the future, but I don't 
think I'd try to do it at this point since we're not making that kind of check 
with any of the other class expressions (unions, property restrictions, etc).


---
If your project is set up for it, you can reply to this email and have your
reply appear on GitHub as well. If your project does not have this feature
enabled and wishes so, or if the feature is enabled but not working, please
contact infrastructure at infrastruct...@apache.org or file a JIRA ticket
with INFRA.
---

Reply via email to