/* Copyright 2009 by the Oxford University Computing Laboratory This file is part of HermiT. HermiT is free software: you can redistribute it and/or modify it under the terms of the GNU Lesser General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. HermiT is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public License for more details. You should have received a copy of the GNU Lesser General Public License along with HermiT. If not, see <http://www.gnu.org/licenses/>. */ package org.semanticweb.HermiT.debugger.commands; import java.io.CharArrayWriter; import java.io.PrintWriter; import java.util.Set; import java.util.TreeSet; import org.semanticweb.HermiT.debugger.Debugger; import org.semanticweb.HermiT.debugger.Printing; import org.semanticweb.HermiT.model.Concept; import org.semanticweb.HermiT.model.DLPredicate; import org.semanticweb.HermiT.tableau.ExtensionTable; import org.semanticweb.HermiT.tableau.Node; public class QueryCommand extends AbstractCommand { public QueryCommand(Debugger debugger) { super(debugger); } public String getCommandName() { return "query"; } public String[] getDescription() { return new String[] { "","prints whether there is a clash", "?|predicate [?|nodeID]+","prints all facts matching the query; ? is a joker", }; } public void printHelp(PrintWriter writer) { writer.println("usage: query"); writer.println(" Prints whether the model contains a clash."); writer.println("usage: ?|predicate [?|nodeID]+"); writer.println(" Prints all facts matching the query, which is a partially specified atom."); writer.println(" Parts of the atom are either specified fully, or by using ? as a joker."); } public void execute(String[] args) { Object[] tuple=new Object[args.length-1]; if (tuple.length==0) { // no further argument, so just check for a clash if (m_debugger.getTableau().getExtensionManager().containsClash()) m_debugger.getOutput().println("The model currently contains a clash."); else m_debugger.getOutput().println("The modelcurrently does not contain a clash."); } else { // further query arguments if ("?".equals(args[1])) tuple[0]=null; else { try { tuple[0]=getDLPredicate(args[1]); } catch (Exception e) { m_debugger.getOutput().println("Invalid predicate '"+args[1]+"':"+e.getMessage()); } if (tuple[0]==null) { m_debugger.getOutput().println("Invalid predicate '"+args[1]+"'."); return; } } for (int index=1;index<tuple.length;index++) { String nodeIDString=args[index+1]; if ("?".equals(nodeIDString)) // no particular nodeID given tuple[index]=null; else { int nodeID; try { nodeID=Integer.parseInt(nodeIDString); } catch (NumberFormatException e) { m_debugger.getOutput().println("Invalid node ID."); return; } tuple[index]=m_debugger.getTableau().getNode(nodeID); if (tuple[index]==null) { m_debugger.getOutput().println("Node with ID '"+nodeID+"' not found."); return; } } } boolean[] boundPositions=new boolean[tuple.length]; for (int index=0;index<tuple.length;index++) if (tuple[index]!=null) boundPositions[index]=true; ExtensionTable extensionTable=m_debugger.getTableau().getExtensionManager().getExtensionTable(tuple.length); ExtensionTable.Retrieval retrieval=extensionTable.createRetrieval(boundPositions,ExtensionTable.View.TOTAL); System.arraycopy(tuple,0,retrieval.getBindingsBuffer(),0,tuple.length); retrieval.open(); Set<Object[]> facts=new TreeSet<Object[]>(Printing.FactComparator.INSTANCE); Object[] tupleBuffer=retrieval.getTupleBuffer(); while (!retrieval.afterLast()) { facts.add(tupleBuffer.clone()); retrieval.next(); } CharArrayWriter buffer=new CharArrayWriter(); PrintWriter writer=new PrintWriter(buffer); writer.println("==========================================="); StringBuffer queryName=new StringBuffer("Query:"); writer.print("Query:"); for (int index=1;index<args.length;index++) { writer.print(' '); writer.print(args[index]); queryName.append(' '); queryName.append(args[index]); } writer.println(); writer.println("==========================================="); for (Object[] fact : facts) { writer.print(' '); printFact(fact,writer); writer.println(); } writer.println("==========================================="); writer.flush(); showTextInWindow(buffer.toString(),queryName.toString()); selectConsoleWindow(); } } protected void printFact(Object[] fact,PrintWriter writer) { Object dlPredicate=fact[0]; if (dlPredicate instanceof Concept) writer.print(((Concept)dlPredicate).toString(m_debugger.getPrefixes())); else if (dlPredicate instanceof DLPredicate) writer.print(((DLPredicate)dlPredicate).toString(m_debugger.getPrefixes())); else throw new IllegalStateException("Internal error: invalid predicate."); writer.print('['); for (int position=1;position<fact.length;position++) { if (position!=1) writer.print(','); writer.print(((Node)fact[position]).getNodeID()); } writer.print(']'); } }