降低 Jena 函数的性能 "ResultSetFactory.copyResults()"

Decreasing Performance of Jena function "ResultSetFactory.copyResults()"

我正在使用 SPARQL 查询我的 ontology,但我发现性能下降,我请求的查询越多,性能就越差。一开始PC端查询需要150ms左右,30.query需要670ms,100.query需要7秒多! 它取决于查询 and/or ontology,但直到现在,我都能在每个 ontology.

中找到它

"ResultSetRewindable r = ResultSetFactory.copyResults(results);" 行是造成时间泄漏的原因,但也可以通过避免导致类似行为的行来解决问题。

我使用了披萨 ontology (https://ontohub.org/pizza/pizza.owl) 和以下代码。此外,我使用的是 Jena 2.13 版本。

有人知道如何解决吗?

public static void main(String[] args) throws UnsupportedEncodingException, InterruptedException{
    OntModel model = ModelFactory.createOntologyModel();
    String OWLPath = "pizza.owl";
    String queryString = "PREFIX rdf: <http://www.w3.org/1999/02/22-rdf-syntax-ns#> PREFIX owl: <http://www.w3.org/2002/07/owl#> PREFIX rdfs: <http://www.w3.org/2000/01/rdf-schema#> PREFIX xsd: <http://www.w3.org/2001/XMLSchema#> PREFIX pz: <http://www.co-ode.org/ontologies/pizza/pizza.owl#> SELECT DISTINCT ?x WHERE {     ?b owl:someValuesFrom pz:MozzarellaTopping. ?x rdfs:subClassOf ?b.      ?x rdfs:subClassOf* pz:Pizza.}";
    for(int j=0; j<100;j++){
    double starttime = System.currentTimeMillis();
                InputStream in = FileManager.get().open(OWLPath);
        if (in == null) {
            throw new IllegalArgumentException("File: " + OWLPath + " not found");
        }
        model.read(in, "");

        Query query = QueryFactory.create(queryString);
        QueryExecution qe = QueryExecutionFactory.create(query, model);
        ResultSet results = qe.execSelect();

        ByteArrayOutputStream baos = new ByteArrayOutputStream();   
        PrintStream ps = new PrintStream(baos);

        double time1 = System.currentTimeMillis();
        ResultSetRewindable r = ResultSetFactory.copyResults(results);
        double time2 = System.currentTimeMillis();  

        ResultSetFormatter.out(ps, r, query);
        String queryOutput = new String(baos.toByteArray(), "UTF-8");
        String[] resultText = queryOutput.split("\n");  
        for(int i=0; i<resultText.length;i++){
            System.out.println(resultText[i]);
        }
    double endtime = System.currentTimeMillis();
    System.out.println("Time: "+ (endtime-starttime) +"     Time for ResultSetFactory.copyResults(results): "+ (time2-time1));
    }
 }

这是一个简单的错误。问题是模型没有清理,每次读取 ontology 时,模型大小都会增加。 可以使用以下方式清理模型:

model.removeAll();

或行

model.read(in, "");

可以替换为

Model model = ModelFactory.createDefaultModel().read(in, "");

在2.13和3.3.0版本中都可以正常使用。此外,所需时间减少了 5 倍,因此性能更好且运行稳定。第二个版本只比第一个稍微好一点。