I think it is simpler to reason over real examples, let's consider the following knowledge base:
:eats rdf:type owl:ObjectProperty .
:Vegetable rdf:type owl:Class ;
rdfs:subClassOf owl:Thing .
:Vegetarian rdf:type owl:Class ;
owl:equivalentClass [ rdf:type owl:Restriction ;
owl:onProperty :eats ;
owl:allValuesFrom :Vegetable
] .
:Carrot rdf:type :Vegetable ,
owl:NamedIndividual .
:John rdf:type owl:NamedIndividual , owl:Thing ;
:eats :carrot .
You have some equivalences with your example: hasBar
is eats
, Vegetarian
is SomethingElse
, Vegetable
is Something
, foo
is carrot
and finally x
is John
.
Now you would like to infer that John
is a Vegetarian
(= x
is SomethingElse
).
It makes sense that it doesn't work with an owl:allValuesFrom
. What you are saying here is that all instances of vegetarian, if they have a property, they must have Vegetable in range. So from that you could deduce that carrot
is a vegetable for example, assuming you would know that John is a vegetarian in the first place.
It makes sense in natural language too: In your ontology you only know that John eats a carrot, this doesn't automatically make him a vegetarian (non-vegetarian people eat also carrots).
You could use a owl:someValuesFrom
instead of a owl:allValuesFrom
. This way, you would define every vegetarian has someone that eats some vegetable. In this case if we know that John eats a carrot, therefore he would be classified as vegetarian by the reasoner, based on your definition of the concept vegetarian.
Universal (allValuesFrom
) and existential (someValuesFrom
) restrictions are complicated to understand, there is often no right or wrong solution, it mostly depends to what you want to achieve.