问题
I've been searching for a solution for days now and since there is no forum at Apache Jena I had to create an account at stackoverflow to ask.
My problem is that I need a temporary (deep) copy of an already loaded ontology, namely an object of OntModelImpl
(with some imports but without any attached inference machine). Its purpose is to apply some validation steps on the model which require some SPARQL UPDATE queries to add some automatically generated triples first. These additional triples are only intended for the validation and should not find their way into the original model!
There is no copy- or clone-method on the object itself and through my many searches I couldn’t find any static (?) methods anywhere else to fulfil this purpose. Instead there is some kind of "copy constructor" (not really marked as such) on OntModelImpl
which takes a specification (OntModelSpec
) and a Model
. I tried to use it this way:
workingModel = new OntModelImpl(ontModel.getSpecification(), ontModel);
Where ontModel
is an OntModelImpl
which was previously created through a call of JenaOWLModel.getOntModel()
. The JenaOWLModel
itself is part of the Protégé-3-API and was created through a call to OwlProjectFromReaderCreator.getOwlModel()
. This creator (together with a necessary repository) was used to load the original ontology with its imports. workingModel
denotes my working copy I am trying to create.
The initial problem with the shown code line was that it throws multiple DoesNotExistException
s, a dozen or more call levels beneath. These denote that the import ontologies couldn't be found??? As I mentioned before, the original model is already loaded, inclusive all imports. (I skip some details here to shorten the story.)
Later I found out that I can suppress the exceptions by setting
ontModel.getSpecification().getDocumentManager().setProcessImports(false);
before the constructor-call. From this point everything looked fine, no exceptions anymore, I got two different model objects with the same triple counts in their different graphs (I did a quick compare of the object IDs of all first and second level attributes of the two instances of OntModelImpl
to make sure it is a deep copy). But today I got aware of something strange: There is no problem when adding the validation triples the first time - I write the triple count to stdout before and after the SPARQL-UPDATE-INSERT-requests. But when I call the validation for the second time, the original model does already contain the additional triples!?
That means either the two models are linked somehow I couldn't see or Jena uses some kind of global linking-, maybe caching-mechanism I am not aware of which tries to hold all models with the same URI consistent to each other or something totally different.
So I really need help here! How can I get a copy of an OntModel
(OntModelImpl
) to apply temporary changes which I want to throw away afterwards?
Greetings and thanks for your time
回答1:
The answer from @dr0i did not work for me.
This worked:
Model copy = ModelFactory.createDefaultModel().add(originalModel);
ModelFactory
creates Model
subclasses as well: createInfModel()
, createOntologyModel()
.
I tested with the following logic.
int size = originalModel.size();
Model copy = ModelFactory.createDefaultModel().add(originalModel);
copy.removeAll();
assert originalModel.size() == size;
回答2:
How to make a deep copy of the Model
:
Model copyOfOntModel = ModelFactory.createModelForGraph(ontModel.getGraph());
Then use this to instantiate your new OntModelImpl
:
workingModel = new OntModelImpl(ontModel.getSpecification(),copyOfOntModel);
来源:https://stackoverflow.com/questions/22713884/how-to-clone-or-copy-a-jena-ontology-model-ontmodel-to-apply-temporary-changes