Dear list,

I want to replace all the RDF lists in a model which have contents equal to given input RDF list 'old' with a copies of an RDF list 'fresh'.

Following the advise in https://jena.apache.org/documentation/javadoc/jena/org/apache/jena/rdf/model/RDFList.html#removeList--, I remove all lists equal to 'old' and update old's heads to new copies of fresh.

However, running the code has two results, either it fails with the exception:

Exception in thread "main" org.apache.jena.shared.PropertyNotFoundException: http://www.w3.org/1999/02/22-rdf-syntax-ns#first at org.apache.jena.rdf.model.impl.ModelCom.getRequiredProperty(ModelCom.java:1231) at org.apache.jena.rdf.model.impl.ResourceImpl.getRequiredProperty(ResourceImpl.java:172) at org.apache.jena.rdf.model.impl.RDFListImpl.sameListAs(RDFListImpl.java:876)
    at ListTest.substituteNonEmptyRDFList(ListTest.java:39)
    at ListTest.main(ListTest.java:65)


or it outputs a model where the replaced list seems OK, but does not seem to be recognized as a proper RDF list (due to the lack of terse list formatting):

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

ex:fresh1  ex:hasList  ( ex:B1 ex:B2 ) .

ex:old1  ex:hasList  [ a          rdf:List ;
                       rdf:first  ex:B1 ;
                       rdf:rest   [ a          rdf:List ;
                                    rdf:first  ex:B2 ;
                                    rdf:rest   ()
                                  ]
                     ] .

Running code example and input data attached.

Grateful for all help.

Regards,
Martin G. Skjæveland
import java.util.ArrayList;
import java.util.HashSet;
import java.util.List;
import java.util.Set;

import org.apache.jena.rdf.model.Model;
import org.apache.jena.rdf.model.RDFList;
import org.apache.jena.rdf.model.RDFNode;
import org.apache.jena.rdf.model.Resource;
import org.apache.jena.rdf.model.ResourceFactory;
import org.apache.jena.rdf.model.Statement;
import org.apache.jena.util.FileManager;
import org.apache.jena.vocabulary.RDF;

public class ListTest {
	
	private static Model readModel (String file, String serialisation) {
		return FileManager.get().loadModel(file, serialisation);
	}
	
	// collect all non-empty lists
	public static Set<RDFList> getNonEmptyRDFLists (Model model) {
		Set<RDFList> lists = new HashSet<>();
		for (Resource head : model.listSubjectsWithProperty(RDF.first).toSet()) {
			if (!model.listResourcesWithProperty(RDF.rest, head).hasNext() && // make sure that we are at the first element
					head.canAs(RDFList.class)) {
				lists.add(head.as(RDFList.class));
			}
		}
		return lists;
	}
	
	public static void substituteNonEmptyRDFList (Model model, RDFList old, RDFList fresh) {
		// Remove all old lists:
		List<RDFNode> oldHeads = new ArrayList<>();
		Set<RDFList> lists = getNonEmptyRDFLists(model);
		for (RDFList l : lists) {
			if (l.sameListAs(old)){
				l.removeList();
				oldHeads.add(l);
			}
		}

		// replace pointers to old lists to new copies of fresh lists:
		for (RDFNode n : oldHeads) {
			RDFList freshCopy = fresh.copy();				
			for (Statement s: model.listStatements(null, null, n).toList()) {
				s.changeObject(freshCopy);
			}
		}
	}
	
	public static void main (String[] args) {
		
		// read model
		String file = "src/test/resource/rdf/lists2.ttl";
		Model model = ListTest.readModel(file, "turtle");
		
		// get list to replace: old and fresh
		String ex = "http://example.com#";;
		RDFList old1 = model.listObjectsOfProperty(ResourceFactory.createResource(ex + "old1"), ResourceFactory.createProperty(ex + "hasList")).next().as(RDFList.class);
		RDFList fresh1 = model.listObjectsOfProperty(ResourceFactory.createResource(ex + "fresh1"), ResourceFactory.createProperty(ex + "hasList")).next().as(RDFList.class);
		
		ListTest.substituteNonEmptyRDFList(model, old1, fresh1);
		
		model.write(System.out, "turtle");
	}

}
@prefix rdf:   <http://www.w3.org/1999/02/22-rdf-syntax-ns#> .
@prefix ex:  <http://example.com#> .

ex:old1   ex:hasList (ex:A1 ex:A2 ex:A3) .
ex:fresh1  ex:hasList (ex:B1 ex:B2) .


Reply via email to