Hi,

Answer below....

On Thu, Nov 1, 2012 at 6:49 PM, Nga Chung <ngatch...@gmail.com> wrote:
> Hi all,
>
> I am using jena-fuseki-0.2.4 with TDB.
>
> I ran the following INSERT query:
>
> INSERT DATA {
> <http://example.org#Sub> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <
> http://example.org#Model>.
> <http://example.org#Sub> <http://example.org#hasProperty0> _:a0.
> _:a0 <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <
> http://example.org#Context>.
> _:a0 <http://example.org#hasProperty1> _:a1.
> _:a1 <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <
> http://example.org#Surface>.
> _:a1 <http://example.org#hasProperty2> <http://example.org#Flat>.
> }
>
> and confirmed that these 6 triples were inserted.
>
> I now want to delete all triples associated with the subject,
> http://example.org#Sub.
>
> I ran the following DELETE query:
>
> DELETE { <http://example.org#Sub> ?p ?o. } WHERE { <http://example.org#Sub>
> ?p ?o. }
>
> These 2 triples:
>
> <http://example.org#Sub> <http://www.w3.org/1999/02/22-rdf-syntax-ns#type> <
> http://example.org#Model>.
> <http://example.org#Sub> <http://example.org#hasProperty0> _:a0.
>
> have been removed, but the blank nodes still exist in TDB.

You don't delete nodes, per se. Instead you delete triples. You've
deleted the triples where <http://example.org#Sub> is the subject, but
you inserted several other triples where this was not the subject.

> Is there a way to construct a DELETE query to remove all blank nodes
> associated with the subject, http://example.org#Sub, regardless of the
> length of the path from http://example.org#Sub to the blank nodes?

There are two problems with this.

The first problem is that there is no way to select a previously
unknown property transitively. Ideally, you'd be able to say the
following:

DELETE { ?s ?p ?o } WHERE { <http://example.org#Sub> ?prop* ?s . ?s ?p ?o }

However, this is illegal, since the transitive property cannot be a
variable. That said, in many cases, the number of relevant properties
is usually finite and known ahead of time. In your example, the
properties are rdf:type, ex:hasProperty0, ex:hasProperty1,
ex:hasProperty2. With a finite list like this it's possible to create
an expression that uses all of them:

PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#>
PREFIX ex: <http://example.org#>

DELETE { ?s ?p ?o }
WHERE {ex:Sub (rdf:type | ex:hasProperty0 | ex:hasProperty1 |
ex:hasProperty2 )* ?s. ?s ?p ?o}

This transitively goes down that set of properties finding everything
attached, and then deletes the statements where the found nodes are
subjects. The fact that I used * instead of + means that it also
includes the ex:Sub in the list of subjects.

The second problem is that it can be dangerous. If you've created a
reference to another existing resource then you'd be removing
everything about that resource as well... and if it referred to
another resource it would also remove it. With enough links you could
transitively empty the entire graph. Any properties that can
potentially point to other resources that shouldn't be touched will
need to be left out of the list of properties in the above expression.

Hope this helps.

Regards,
Paul

Reply via email to