#java #sparql #jena #protege
Вопрос:
Я пытаюсь выбрать несколько столбцов в результирующем наборе Jena, а затем привязать их к таблице Java.
Когда я выбираю только один столбец, результирующий набор работает нормально, но когда я выбираю два столбца, в результирующем наборе нет ни одной строки, хотя в нем есть только столбцы:
Вот мой Java-код:
private void btnExecuteSPARQLActionPerformed(java.awt.event.ActionEvent evt) {
try
{
System.out.println("Executing SPARQL..."); // get the name list query
String queryString;
queryString = "PREFIX ssuet:<http://www.semanticweb.org/alinaanjum2/ontologies/2021/6/untitled-ontology-4#> "
txtQuery.getText();
com.hp.hpl.jena.query.ResultSet results = OpenOWL.ExecSparQl(queryString); //all method ExecSparQl from OpenOWL class
ResultSetFormatter.out(results);
// It creates and displays the table
JTable table = new JTable(buildTableModel(results));
JOptionPane.showMessageDialog(null, new JScrollPane(table));
}
catch (Exception ex)
{
System.out.println(ex);
}
}
//CODE ADDITION BY ALINA ANJUM STARTED ON 03-AUGUST-2021
public static DefaultTableModel buildTableModel(com.hp.hpl.jena.query.ResultSet rs)
throws SQLException {
List<String> metaData = rs.getResultVars();
// names of columns
Vector<String> columnNames = new Vector<String>();
int columnCount = metaData.size();
System.out.println(columnCount);
for (int column = 0; column <columnCount; column )
{
columnNames.add(metaData.get(column));
}
// data of the table
Vector<Vector<Object>> data = new Vector<Vector<Object>>();
while (rs.hasNext())
{
QuerySolution sol = rs.nextSolution();
Vector<Object> vector = new Vector<Object>();
for (int columnIndex = 0; columnIndex < columnCount; columnIndex )
{
//vector.add(rs.getObject(columnIndex));
String columnName = columnNames.get(columnIndex);
vector.add(sol.getLiteral(columnName).getString());
}
data.add(vector);
}
return new DefaultTableModel(data, columnNames);
}
Следующий запрос идеально возвращает значения:
SELECT (str(?x) as ?name)
WHERE {
?Person ssuet:hasname ?x.
}
Следующий запрос отлично работает в Protege, но не возвращает значения в результирующем наборе в Java:
SELECT (str(?x) as ?name)
(str(?y) as ?phone)
WHERE {
?Person ssuet:hasname ?x.
?Person ssuet:hasPhoneNumber ?y.
}
Снимок экрана с выводом в Netbeans:
Результаты для 2-го запроса в protege:
Комментарии:
1.
com.hp.hpl.jena.query
— эта версия Йены древняя. В настоящее время Jena работает над версией 4.2.0.2. кроме того, вы должны использовать Java 11, опустить
Vector
класс, следовать своему собственному соглашению об именовании и использоватьhasName
(стиль верблюжьего регистра)3. если ваш второй запрос ничего не возвращает, даже на консоли Netbeans, то данные просто не такие, как в Protege, и запрос не совпадает. Вы проверили это с помощью текстового редактора? Или просто распечатать тройку через Jena API?
4. @Неинформированный пользователь не могли бы вы поделиться полным руководством по новой версии Jena? Я новичок в этом
5. просто используйте Apache Jena с Maven (документы доступны онлайн), а не такой 6-летний сторонний проект, как github.com/softiecode/QueryExpansion если вам не нужно то, что они предоставляют в качестве функций. И они не делают ничего, кроме как загружают онтологию в
OntModel
и затем запускают запрос. Я бы предложил сделать это на родном коде Jena и использовать последнюю версию4.2.0
Ответ №1:
ResultSets
являются итераторами.
Вызов ResultSetFormatter.out(results)
исчерпывает итератор (больше строк нет).
Если вы хотите использовать результат дважды, используйте ResultSetFactory.makeRewindable
его, чтобы получить набор результатов, который можно сбросить до начала.
Комментарии:
1. правильно, ни один из двух quries не будет отображаться как
JTable
— но afaik вопрос также заключался в том, почему второй запрос вообще не показывает никакого набора результатов, даже не в CLI — см. Первый снимок экрана, он возвращает полную таблицу в CLI, но только заголовок для второго2. спасибо @AndyS, но проблема во 2-м запросе. это даже не возвращается в ResultSetFormatter, как сказал неинформированный пользователь.