It looks like I'm not a good Pizzaïolo, problems with simple reasoning

classic Classic list List threaded Threaded
4 messages Options
Reply | Threaded
Open this post in threaded view
|

It looks like I'm not a good Pizzaïolo, problems with simple reasoning

shazz
Hi!

To understand how to use Owlready2, I enriched the Pizza example but the reasoner was not able to find instances which are Veggy and Vegetarian, only the NonVegetarian. I guess I did something wrong but I cannot spot it.

Can you point me to my mistakes ?

Code here: https://github.com/shazz/Owlready2_sandbox/blob/master/pizza.py

Results:
Individuals of NonVegetarianPizza are [pizza_onto.napolitana]
Individuals of VegetarianPizza are []
Individuals of VeganPizza are []

Can somebody explain me alos what means:
* Owlready * Reparenting pizza_onto.VeganPizza: {pizza_onto.Pizza} => {pizza_onto.VegetarianPizza}
* Owlready * Reparenting pizza_onto.napolitana: {pizza_onto.Pizza} => {pizza_onto.NonVegetarianPizza}
* Owlready * (NB: only changes on entities loaded in Python are shown, other changes are done but not listed)

Thanks !
Reply | Threaded
Open this post in threaded view
|

Re: It looks like I'm not a good Pizzaïolo, problems with simple reasoning

Jiba
Administrator
Hi,

The problem you encounter is known as "open world assumption". OWL ontologies and reasoners assume that anything that is not forbidden is possible. Here, your margarita has cheese and tomato. But you do not state that it has no other topping, so the reasoner cannot conclude that it is vegetarian.

If you want to make this deduction, you need to assert that margarita has only cheese and tomato:

margarita.is_a.append(has_topping.only(Cheese | Tomato))

You may also use the close_world() function of Owlready, which can add those restrictions automatically.


> Can somebody explain me alos what means:
> * Owlready * Reparenting pizza_onto.VeganPizza: {pizza_onto.Pizza} => {pizza_onto.VegetarianPizza}
> * Owlready * Reparenting pizza_onto.napolitana: {pizza_onto.Pizza} => {pizza_onto.NonVegetarianPizza}
> * Owlready * (NB: only changes on entities loaded in Python are shown, other changes are done but not listed)

These are information printed by Owlready. It means that VeganPizza has been reparented from Pizza to VegetarianPizza, and napolitana from Pizza to NonVegetarianPizza.

You can suppress those prints with the debug=0 parameter when calling sync_reasoner().

Jiba
Reply | Threaded
Open this post in threaded view
|

Re: It looks like I'm not a good Pizzaïolo, problems with simple reasoning

shazz
This post was updated on .
Thanks Jiba,

Ok I should have looked more carefully of this "open world" concept, that's not an option :)

So, thanks to your advice, it works!
But not the close_world(onto_pizza.Pizza):

Traceback (most recent call last):
  File "pizza.py", line 38, in <module>
    owlready2.sync_reasoner(infer_property_values = True)
  File "C:\Work\Analytics\git\EDM\OWL2\.venv37\lib\site-packages\owlready2\reasoning.py", line 137, in sync_reasoner_hermit
    raise OwlReadyInconsistentOntologyError()
owlready2.base.OwlReadyInconsistentOntologyError

Then.. I tried a more complicated pizza example. And I thought I understood things... not at all:

code: https://github.com/shazz/Owlready2_sandbox/blob/master/my_pizza.py
result:
Inferred classes
onto_pizza.a_Margarita is infered as [onto_pizza.has_ingredient.only(onto_pizza.Cheese | onto_pizza.Tomato), onto_pizza.Margarita] and that's True and False!
onto_pizza.a_Pizzananas is infered as [onto_pizza.has_ingredient.only(onto_pizza.Pineapple | onto_pizza.Tomato | onto_pizza.Ham), onto_pizza.Pizzananas] and that's True and False!
onto_pizza.a_Portlandia is infered as [onto_pizza.has_ingredient.only(onto_pizza.Tomato), onto_pizza.Portlandia] and that's True and False!
onto_pizza.a_Napolitana is infered as [onto_pizza.has_ingredient.only(onto_pizza.Tomato | onto_pizza.Ham | onto_pizza.Mozzarella), onto_pizza.Napolitana] and that's True and False!
onto_pizza.a_Indiana is infered as [onto_pizza.has_ingredient.only(onto_pizza.Mango), onto_pizza.VeganPizza, onto_pizza.Indiana] and that's True and True!


 - Why NonVeggyPizza pizzas are not infered (they only need meat)
 - I also tried to add the exactly constraint but never worked, any idea ?
 - If I change:

    p = Pizza("a_Margarita")
    p.has_ingredient.append(Mozzarella())
    p.has_ingredient.append(Tomato())
    p.is_a.append(has_ingredient.only(Cheese | Tomato))

to
   ...
   p.is_a.append(has_ingredient.only(Mozzarella| Tomato))

It doesn't work, inference don't work with subtypes ?

That's really not obvious :)


Reply | Threaded
Open this post in threaded view
|

Re: It looks like I'm not a good Pizzaïolo, problems with simple reasoning

Jiba
Administrator
Hi,

> * Owlready * Reparenting onto_pizza.Napolitana: {onto_pizza.Pizza} => {onto_pizza.NonVeggyPizza, onto_pizza.Margarita}

This means that Napolitana is inferred as a Margarita. It is logic, because anything that has tomato and cheese is a Margarita, and Napolitana has both tomato and cheese. It also has Meat, but the definition of Margarita does not specify that it must have ONLY tomato and cheese.

You also need to state that Cheese, Tomato, Meat, etc are disjoint (using AllDisjoint).

This is "cold logic", and yes, it is not obvious... You should refer to an OWL tutorial or documentation, those questions are not specific to Owlready.

Jiba