{ "cells": [ { "cell_type": "markdown", "metadata": {}, "source": [ "# Queries: using the search module\n", "\n", "
\n", "\n", "[![Binder](https://mybinder.org/badge_logo.svg)](https://mybinder.org/v2/gh/simphony/docs/v4.0.0?filepath=docs%2Fusage%2Fsessions%2Fsearch.ipynb \"Click to run this tutorial yourself!\")\n", " \n", "
" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The search module enables more advanced queries of session's contents when compared to the [methods from the session object](queries.ipynb). It is intended to offer a pythonic approach to querying the session, but still, it has significant efficiency and expresivity limitations. An additional constraint is the topology of the graph that the relationships (and annotations) between the individuals form, as the functions from the module work **traversing the graph from a given initial individual**. Therefore, whenever you require more advanced or more performant queries, use [SPARQL](sparql.ipynb)." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "SimPhoNy's search module is located under `simphony_osp.tools.search` and can be imported as follows." ] }, { "cell_type": "code", "execution_count": 1, "metadata": {}, "outputs": [], "source": [ "from simphony_osp.tools import search" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The following functions are available:\n", "\n", "- [find](#find)\n", "- [find_by_identifier](#find_by_identifier)\n", "- [find_by_class](#find_by_class)\n", "- [find_by_attribute](#find_by_attribute)\n", "- [find_relationships](#find_relationships)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "A `sparql` function is also provided by the module. However, it is not covered in this section, [but the next one](sparql.ipynb)." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "To see how these functions work, let's set-up an example with two cities, Freiburg and Paris." ] }, { "cell_type": "code", "execution_count": 2, "metadata": {}, "outputs": [], "source": [ "from simphony_osp.namespaces import city, owl, rdfs\n", "from simphony_osp.session import core_session\n", "\n", "# Create a city called \"Freiburg\"\n", "freiburg = city.City(name=\"Freiburg\", coordinates=[47.997791, 7.842609])\n", "freiburg_neighborhoods = [\n", " city.Neighborhood(name=name, coordinates=coordinates)\n", " for name, coordinates in [\n", " ('Altstadt', [47.99525, 7.84726]),\n", " ('Stühlinger', [47.99888, 7.83774]),\n", " ('Neuburg', [48.00021, 7.86084]),\n", " ('Herdern', [48.00779, 7.86268]),\n", " ('Brühl', [48.01684, 7.843]),\n", " ]\n", "]\n", "freiburg_citizens = {\n", " city.Citizen(name='Nikola', age=35,\n", " iri=\"http://example.org/entities#Nikola\"),\n", " city.Citizen(name='Lena', age=70,\n", " iri=\"http://example.org/entities#Lena\"),\n", "}\n", "freiburg[city.hasPart] |= freiburg_neighborhoods\n", "freiburg[city.hasInhabitant] |= freiburg_citizens\n", "\n", "# Create a city called \"Paris\"\n", "paris = city.City(name=\"Paris\", coordinates=[48.85333, 2.34885])\n", "paris_neighborhoods = {\n", " city.Neighborhood(name=name, coordinates=coordinates)\n", " for name, coordinates in [\n", " ('Louvre', [48.86466, 2.33487]),\n", " ('Bourse', [48.86864, 2.34146]),\n", " ('Temple', [48.86101, 2.36037]),\n", " ('Hôtel-de-Ville', [48.85447, 2.35902]),\n", " ('Panthéon', [48.84466, 2.3471]),\n", " ]\n", "}\n", "paris_citizens = {\n", " city.Citizen(name='François', age=32)\n", "}\n", "paris[city.hasPart] |= paris_neighborhoods\n", "paris[city.hasInhabitant] = paris_citizens" ] }, { "cell_type": "code", "execution_count": 3, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#3385d37b-8bb3-48bf-94ea-fcc0397f6466\n", "\n", "3385d37b...466\n", "classes: Neighborhood (city)\n", "name: Brühl\n", "coordinates: [48.01684  7.843  ]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#a6167e38-851e-4fb8-b5a7-c4c0d929e7ef\n", "\n", "a6167e38...7ef\n", "classes: Neighborhood (city)\n", "name: Louvre\n", "coordinates: [48.86466  2.33487]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315\n", "\n", "db7348a9...315\n", "classes: City (city)\n", "name: Freiburg\n", "coordinates: [47.997791  7.842609]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#3385d37b-8bb3-48bf-94ea-fcc0397f6466\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "http___example.org_entities#Lena\n", "\n", "http://example.org/entities#Lena\n", "classes: Citizen (city)\n", "name: Lena\n", "age: 70\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->http___example.org_entities#Lena\n", "\n", "\n", "has inhabitant (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#04ea43f7-c381-400b-97f2-8d5b4fb13d19\n", "\n", "04ea43f7...d19\n", "classes: Neighborhood (city)\n", "name: Stühlinger\n", "coordinates: [47.99888  7.83774]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#04ea43f7-c381-400b-97f2-8d5b4fb13d19\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#1fada633-0fd2-47c0-b800-2c27a2d450a7\n", "\n", "1fada633...0a7\n", "classes: Neighborhood (city)\n", "coordinates: [48.00779  7.86268]\n", "name: Herdern\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#1fada633-0fd2-47c0-b800-2c27a2d450a7\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#67be995a-a882-493b-8f70-ed17067cb8c6\n", "\n", "67be995a...8c6\n", "classes: Neighborhood (city)\n", "coordinates: [47.99525  7.84726]\n", "name: Altstadt\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#67be995a-a882-493b-8f70-ed17067cb8c6\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "http___example.org_entities#Nikola\n", "\n", "http://example.org/entities#Nikola\n", "classes: Citizen (city)\n", "name: Nikola\n", "age: 35\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->http___example.org_entities#Nikola\n", "\n", "\n", "has inhabitant (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#02c61947-7684-43a7-9882-086295a5305e\n", "\n", "02c61947...05e\n", "classes: Neighborhood (city)\n", "coordinates: [48.00021  7.86084]\n", "name: Neuburg\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#02c61947-7684-43a7-9882-086295a5305e\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#618889d2-ee0f-4b7e-8baa-c1ca930402b3\n", "\n", "618889d2...2b3\n", "classes: City (city)\n", "name: Paris\n", "coordinates: [48.85333  2.34885]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#618889d2-ee0f-4b7e-8baa-c1ca930402b3->https___www.simphony-osp.eu_entity#a6167e38-851e-4fb8-b5a7-c4c0d929e7ef\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#9c142ddc-bdb1-487a-8837-d917cbd527c1\n", "\n", "9c142ddc...7c1\n", "classes: Neighborhood (city)\n", "coordinates: [48.86101  2.36037]\n", "name: Temple\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#618889d2-ee0f-4b7e-8baa-c1ca930402b3->https___www.simphony-osp.eu_entity#9c142ddc-bdb1-487a-8837-d917cbd527c1\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#3b4fcff1-062c-4ba3-a2a8-f3b8e26f20cb\n", "\n", "3b4fcff1...0cb\n", "classes: Neighborhood (city)\n", "coordinates: [48.85447  2.35902]\n", "name: Hôtel-de-Ville\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#618889d2-ee0f-4b7e-8baa-c1ca930402b3->https___www.simphony-osp.eu_entity#3b4fcff1-062c-4ba3-a2a8-f3b8e26f20cb\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#b1a0e59e-a2a6-430e-9e24-65fac7ee74b5\n", "\n", "b1a0e59e...4b5\n", "classes: Citizen (city)\n", "age: 32\n", "name: François\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#618889d2-ee0f-4b7e-8baa-c1ca930402b3->https___www.simphony-osp.eu_entity#b1a0e59e-a2a6-430e-9e24-65fac7ee74b5\n", "\n", "\n", "has inhabitant (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#6486c12a-33b8-4677-aef2-18d2553f9c99\n", "\n", "6486c12a...c99\n", "classes: Neighborhood (city)\n", "name: Bourse\n", "coordinates: [48.86864  2.34146]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#618889d2-ee0f-4b7e-8baa-c1ca930402b3->https___www.simphony-osp.eu_entity#6486c12a-33b8-4677-aef2-18d2553f9c99\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#df02e711-9de1-4981-b222-f7e50ed2f798\n", "\n", "df02e711...798\n", "classes: Neighborhood (city)\n", "name: Panthéon\n", "coordinates: [48.84466  2.3471 ]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#618889d2-ee0f-4b7e-8baa-c1ca930402b3->https___www.simphony-osp.eu_entity#df02e711-9de1-4981-b222-f7e50ed2f798\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 3, "metadata": {}, "output_type": "execute_result" } ], "source": [ "from simphony_osp.tools import semantic2dot # explained in a later section\n", "\n", "semantic2dot(freiburg, *freiburg_neighborhoods, *freiburg_citizens,\n", " paris, *paris_neighborhoods, *paris_citizens)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "
\n", "
Tip
\n", " \n", "On most web browsers (including mobile ones), you can right-click the picture above and then click \"open in new tab\" to see the picture in its full size.\n", " \n", "
" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The most important detail to keep in mind is that the functions above do not act on a session object, but on an ontology individual object that has to be provided beforehand. They perform the search by **traversing the relationships and annotations in the graph starting from the given individual**.\n", " \n", "This is the precisely the reason why a directed graph with two [weakly connected components](https://en.wikipedia.org/wiki/Connectivity_(graph_theory)) is provided as example: it illustrates that it is impossible to find individuals from one of the components if the search function is called on an individual belonging to another component. Head to the first subsection, dealing with the function [find](#find), to see this behavior in action." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## `find`" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The function `find` traverses the graph starting from a given _root_ individual, following only relationships that are a subclass of the _given relationships_, and annotations that are a subclass of the _given annotations_. Along the path, it verifies a given _criterion_ on each ontology individual it finds, and then returns the matching individuals." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "To clarify how it works, several calls of increasing difficulty to this function, applied to the graph constructed at the top of this page, are shown as examples." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The simplest call just needs the positional argument `root`. As no relationships nor annotations are provided, all relationships and annotations are followed. Similarly, as no criterion is provided, it is always assumed to be satisfied. " ] }, { "cell_type": "code", "execution_count": 4, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#3385d37b-8bb3-48bf-94ea-fcc0397f6466\n", "\n", "3385d37b...466\n", "classes: Neighborhood (city)\n", "name: Brühl\n", "coordinates: [48.01684  7.843  ]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315\n", "\n", "db7348a9...315\n", "classes: City (city)\n", "name: Freiburg\n", "coordinates: [47.997791  7.842609]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#3385d37b-8bb3-48bf-94ea-fcc0397f6466\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "http___example.org_entities#Lena\n", "\n", "http://example.org/entities#Lena\n", "classes: Citizen (city)\n", "name: Lena\n", "age: 70\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->http___example.org_entities#Lena\n", "\n", "\n", "has inhabitant (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#04ea43f7-c381-400b-97f2-8d5b4fb13d19\n", "\n", "04ea43f7...d19\n", "classes: Neighborhood (city)\n", "name: Stühlinger\n", "coordinates: [47.99888  7.83774]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#04ea43f7-c381-400b-97f2-8d5b4fb13d19\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#1fada633-0fd2-47c0-b800-2c27a2d450a7\n", "\n", "1fada633...0a7\n", "classes: Neighborhood (city)\n", "coordinates: [48.00779  7.86268]\n", "name: Herdern\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#1fada633-0fd2-47c0-b800-2c27a2d450a7\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#67be995a-a882-493b-8f70-ed17067cb8c6\n", "\n", "67be995a...8c6\n", "classes: Neighborhood (city)\n", "coordinates: [47.99525  7.84726]\n", "name: Altstadt\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#67be995a-a882-493b-8f70-ed17067cb8c6\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n", "http___example.org_entities#Nikola\n", "\n", "http://example.org/entities#Nikola\n", "classes: Citizen (city)\n", "name: Nikola\n", "age: 35\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->http___example.org_entities#Nikola\n", "\n", "\n", "has inhabitant (city)\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#02c61947-7684-43a7-9882-086295a5305e\n", "\n", "02c61947...05e\n", "classes: Neighborhood (city)\n", "coordinates: [48.00021  7.86084]\n", "name: Neuburg\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->https___www.simphony-osp.eu_entity#02c61947-7684-43a7-9882-086295a5305e\n", "\n", "\n", "has part (city)\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 4, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = list(\n", " search.find(freiburg)\n", ")\n", "\n", "semantic2dot(*found)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "As it can be seen above, when using `freiburg` as the root object, the result is the subgraph of all ontology individuals reachable from `freiburg`. None of the citizens or neighborhoods of `paris` are returned, as they cannot be reached from the `freiburg` individual." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "To increase the complexity of the query, the relationships to be followed can be limited to the subclasses of various selected relationships using the `rel` keyword arugment. For example, let's restrict the search to inhabitants and workers of Freiburg (as well as Freiburg itself)." ] }, { "cell_type": "code", "execution_count": 5, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315\n", "\n", "db7348a9...315\n", "classes: City (city)\n", "name: Freiburg\n", "coordinates: [47.997791  7.842609]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "http___example.org_entities#Nikola\n", "\n", "http://example.org/entities#Nikola\n", "classes: Citizen (city)\n", "name: Nikola\n", "age: 35\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->http___example.org_entities#Nikola\n", "\n", "\n", "has inhabitant (city)\n", "\n", "\n", "\n", "http___example.org_entities#Lena\n", "\n", "http://example.org/entities#Lena\n", "classes: Citizen (city)\n", "name: Lena\n", "age: 70\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315->http___example.org_entities#Lena\n", "\n", "\n", "has inhabitant (city)\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 5, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = list(\n", " search.find(\n", " freiburg,\n", " rel=(city.hasInhabitant, city.hasWorker) # if only one relationship has to be considered, just pass it directly (i.e. `rel=city.hasInhabitant`)\n", " ) \n", ")\n", "\n", "semantic2dot(*found)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "
\n", "
Note
\n", "\n", "There is a similar keyword argument `annotation` that can be used to constrain the ontology annotations to follow. Just like for the `rel` argument, it can take as values either a single annotation or several ones. However, in addition, it also accepts boolean values. Setting it to `True` means following all annotations (the default value), while setting it to `False` means following no annotations at all.\n", "\n", "
" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "The next complexity step is passing a function as search criterion. For example, one may want to restrict the search to persons that are more than 40 years old." ] }, { "cell_type": "code", "execution_count": 6, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "http___example.org_entities#Lena\n", "\n", "http://example.org/entities#Lena\n", "classes: Citizen (city)\n", "name: Lena\n", "age: 70\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 6, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = list(\n", " search.find(\n", " freiburg,\n", " criterion=lambda individual: individual.is_a(city.Person) and individual.age > 40,\n", " rel=(city.hasInhabitant, city.hasWorker)\n", " ) \n", ")\n", "\n", "semantic2dot(*found)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Note that `freiburg` itself does not satisfy the given criterion, and thus it is excluded from the results." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "That is all! You have mastered the `find` function, although there are still two little details that allow to control the algorithm and the output." ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Relaxing the criterion to just requiring the results to be persons and re-running the search with the keyword argument `find_all=False` causes the search to return only the first individual it finds." ] }, { "cell_type": "code", "execution_count": 7, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "http___example.org_entities#Nikola\n", "\n", "http://example.org/entities#Nikola\n", "classes: Citizen (city)\n", "name: Nikola\n", "age: 35\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 7, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = search.find(\n", " freiburg,\n", " criterion=lambda individual: individual.is_a(city.Person),\n", " rel=(city.hasInhabitant, city.hasWorker),\n", " find_all=False,\n", ") \n", "\n", "semantic2dot(found)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Lastly, the maximum depth of the search can be adjusted using the `max_depth` parameter. Try setting it to `0`, it should yield no results!" ] }, { "cell_type": "code", "execution_count": 8, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 8, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = list(\n", " search.find(\n", " freiburg,\n", " criterion=lambda individual: individual.is_a(city.Person),\n", " rel=(city.hasInhabitant, city.hasWorker),\n", " max_depth=0,\n", " ) \n", ")\n", "\n", "semantic2dot(*found)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "## `find_by_identifier`" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This function is constructed as a call to [find](#find), but with the criterion fixed to matching the given identifier. \n", "\n", "The positional arguments `root` and keyword arguments `rel` and `annotation` behave exactly like in [find](#find). An additional positional argument, `identifier` is required. The keyword arguments `criterion`, `find_all` and `max_depth` are not available, as they are fixed to: matching the given identifier, `False` (as identifiers are unique) and unlimited. \n", "\n", "Therefore, this function yields either `None` or a single ontology individual whose identifier matches the given one." ] }, { "cell_type": "code", "execution_count": 9, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "http___example.org_entities#Lena\n", "\n", "http://example.org/entities#Lena\n", "classes: Citizen (city)\n", "name: Lena\n", "age: 70\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 9, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = search.find_by_identifier(\n", " freiburg,\n", " \"http://example.org/entities#Lena\",\n", " rel=owl.topObjectProperty,\n", ") \n", "\n", "semantic2dot(found)" ] }, { "cell_type": "markdown", "metadata": { "tags": [] }, "source": [ "## `find_by_class`" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "This function is also constructed as a call to [find](#find), but with the criterion fixed to the individual belonging to a specific ontology class. " ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Just like before, the positional arguments `root` and keyword arguments `rel` and `annotation` behave exactly like in [find](#find). An additional positional argument, `oclass` is required. The keyword arguments `criterion`, `find_all` and `max_depth` are not available, as they are fixed to: the individual belonging to the given class, `True` (as identifiers are unique) and unlimited. " ] }, { "cell_type": "code", "execution_count": 10, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "http___example.org_entities#Nikola\n", "\n", "http://example.org/entities#Nikola\n", "classes: Citizen (city)\n", "name: Nikola\n", "age: 35\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n", "http___example.org_entities#Lena\n", "\n", "http://example.org/entities#Lena\n", "classes: Citizen (city)\n", "name: Lena\n", "age: 70\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 10, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = list(search.find_by_class(\n", " freiburg,\n", " city.Person,\n", " rel=owl.topObjectProperty,\n", "))\n", "\n", "semantic2dot(*found)" ] }, { "cell_type": "markdown", "metadata": { "tags": [] }, "source": [ "## `find_by_attribute`" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Finds individuals that have a matching attribute value. `find_all` is set to `True` and `max_depth` to unlimited.\n", "\n", "For example, looking for individuals that are 35 years old yields Nikola." ] }, { "cell_type": "code", "execution_count": 11, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "http___example.org_entities#Nikola\n", "\n", "http://example.org/entities#Nikola\n", "classes: Citizen (city)\n", "name: Nikola\n", "age: 35\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 11, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = list(search.find_by_attribute(\n", " freiburg,\n", " city.age,\n", " 35,\n", " rel=owl.topObjectProperty,\n", "))\n", "\n", "semantic2dot(*found)" ] }, { "cell_type": "markdown", "metadata": { "tags": [] }, "source": [ "## `find_relationships`" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "In this case, individuals that are attached to any other individual through the given relationship (the _source_ individuals of the relationship) are returned. `find_all` is set to `True` and `max_depth` to unlimited." ] }, { "cell_type": "code", "execution_count": 12, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315\n", "\n", "db7348a9...315\n", "classes: City (city)\n", "name: Freiburg\n", "coordinates: [47.997791  7.842609]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 12, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = list(search.find_relationships(\n", " freiburg,\n", " city.hasInhabitant, # the relationship used as criterion\n", " rel=owl.topObjectProperty, # the usual `rel` argument, only this and sub-relationships will be traversed during the search\n", "))\n", "\n", "semantic2dot(*found)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "Note that however, by default sub-relationships of the given relationship are not considered. This can be demonstrated using `owl.topObjectProperty` as relationship, as no results are yielded when doing so" ] }, { "cell_type": "code", "execution_count": 13, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 13, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = list(search.find_relationships(\n", " freiburg,\n", " owl.topObjectProperty, # the relationship used as criterion\n", " rel=owl.topObjectProperty, # the usual `rel` argument, only this and sub-relationships will be traversed during the search\n", "))\n", "\n", "semantic2dot(*found)" ] }, { "cell_type": "markdown", "metadata": {}, "source": [ "unless the keyword argument `find_sub_relationships` is set to `True`." ] }, { "cell_type": "code", "execution_count": 14, "metadata": {}, "outputs": [ { "data": { "image/svg+xml": [ "\n", "\n", "\n", "\n", "\n", "\n", "SimPhoNy semantic2dot\n", "\n", "\n", "\n", "https___www.simphony-osp.eu_entity#db7348a9-ae67-4ca2-83a8-7ee647d3a315\n", "\n", "db7348a9...315\n", "classes: City (city)\n", "name: Freiburg\n", "coordinates: [47.997791  7.842609]\n", "session: 0x55a55d85c140\n", "\n", "\n", "\n" ], "text/plain": [ "" ] }, "execution_count": 14, "metadata": {}, "output_type": "execute_result" } ], "source": [ "found = list(search.find_relationships(\n", " freiburg,\n", " owl.topObjectProperty, # the relationship used as criterion\n", " find_sub_relationships=True,\n", " rel=owl.topObjectProperty, # the usual `rel` argument, only this and sub-relationships will be traversed during the search\n", "))\n", "\n", "semantic2dot(*found)" ] } ], "metadata": { "kernelspec": { "display_name": "Python 3", "language": "python", "name": "python3" }, "language_info": { "codemirror_mode": { "name": "ipython", "version": 3 }, "file_extension": ".py", "mimetype": "text/x-python", "name": "python", "nbconvert_exporter": "python", "pygments_lexer": "ipython3", "version": "3.8.12" }, "toc-showcode": false, "toc-showtags": true }, "nbformat": 4, "nbformat_minor": 4 }