Mysql
 sql >> Database >  >> RDS >> Mysql

Query SPARQL per ottenere tutti i genitori di un nodo

I tuoi dati possono essere rappresentati in RDF come data.n3 :

@prefix : <http://example.org/> .
@prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#> .

:Network rdfs:subClassOf :Main .

:ATM rdfs:subClassOf :Network .
:ARPANET rdfs:subClassOf :Network .

:Software rdfs:subClassOf :Main .

:Linux rdfs:subClassOf :Software .
:Windows rdfs:subClassOf :Software .

:XP rdfs:subClassOf :Windows .
:Win7 rdfs:subClassOf :Windows .
:Win8 rdfs:subClassOf :Windows .

Da qui, vuoi solo una query SPARQL che trovi tutte le cose collegate a una particolare classe da un percorso (incluso il percorso vuoto) di rdfs:subClassOf proprietà.

prefix : <http://example.org/>
prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#>

select ?superclass where { 
  :Win7 rdfs:subClassOf* ?superclass
}
--------------
| superclass |
==============
| :Win7      |
| :Windows   |
| :Software  |
| :Main      |
--------------

I risultati in quella query non sono necessariamente ordinati in base alla loro posizione nel percorso (sebbene in questo caso lo siano). Se ne hai bisogno in ordine, puoi farlo (che si basa su questa risposta sul calcolo della posizione di elementi in un elenco RDF ):

prefix : <http://example.org/>
prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#>

select ?class where { 
  :Win7 rdfs:subClassOf* ?mid .
  ?mid rdfs:subClassOf* ?class .
}
group by ?class
order by count(?mid)

Questo trova ogni antenato ?class di :Win7 così come ogni ?mid antenato intermedio. Per l'antenato ?class , la distanza viene calcolata come il numero di relazioni intermedie tra (count(?mid) ). Ordina i risultati in base a quella distanza, quindi :Win7 è l'antenato più vicino, :Windows dopo, e così via.

Puoi anche eseguire alcune delle fantastiche formattazioni che desideri in questo modo:

prefix : <http://example.org/>
prefix rdfs: <http://www.w3.org/2000/01/rdf-schema#>

select (group_concat( ?name ; separator="--" )  as ?path) where {
  {
    select ?name where { 
      :Win7 rdfs:subClassOf* ?mid .
      ?mid rdfs:subClassOf* ?class .
      bind( strAfter( str(?class), "http://example.org/") as ?name )
    }
    group by ?class ?name
    order by count(?mid)
  }
}
-----------------------------------
| path                            |
===================================
| "Win7--Windows--Software--Main" |
-----------------------------------

potrebbe essere possibile eseguire alcune elaborazioni di stringhe più elaborate e ottenere la stringa multilinea. Potresti esaminare l'ultima parte di questa risposta dove c'è una formattazione di fantasia per una matrice ben allineata per le idee.