steve@0: package org.qmul.eecs.c4dm.sia; steve@0: stevenh@67: import java.util.ArrayList; steve@0: import java.util.Collections; steve@0: import java.util.Iterator; steve@0: import java.util.List; steve@0: stevenh@67: import org.qmul.eecs.c4dm.sia.exceptions.DimensionException; steve@0: import org.qmul.eecs.c4dm.sia.model.Datapoint; stevenh@67: import org.qmul.eecs.c4dm.sia.model.NDimensionalObject; stevenh@67: import org.qmul.eecs.c4dm.sia.model.SiatecX; stevenh@13: import org.qmul.eecs.c4dm.sia.model.VectorTable; steve@0: import org.qmul.eecs.c4dm.sia.model.VectorTableElement; stevenh@13: import org.qmul.eecs.c4dm.sia.utilities.Display; steve@0: steve@0: import com.hp.hpl.jena.ontology.OntModel; stevenh@43: import com.hp.hpl.jena.ontology.OntModelSpec; steve@0: import com.hp.hpl.jena.rdf.model.ModelFactory; steve@0: steve@0: /** steve@0: *

stevenh@5: * Title: SiaMain steve@0: *

steve@0: *

stevenh@67: * Description: An RDF/OWL/Java implementation of the SIA and SIATEC pattern discovery algorithms. stevenh@67: * See "Algorithms for discovering repeated patterns in multidimensional representations of polyphonic music" stevenh@67: * by Meredith, D. and Lemström, K. and Wiggins, G.A. stevenh@67: * Optionally takes a single command line argument file path to an N3 ontology file, otherwise uses a stevenh@67: * hardcoded file path. stevenh@67: * Writes SIA and SIATEC result to stdout and writes the entire RDF model to the TDB dataset described in stevenh@67: * src/assemblers/tdb-assembler.ttl steve@0: *

steve@0: * stevenh@5: * @author Steve Hargreaves, C4DM, Queen Mary University of London steve@0: */ steve@0: public class SiaMain { stevenh@43: stevenh@67: // The ontology loaded as dataset stevenh@67: public static String ontology = "file:src/rdf/siaTestDatapointOntology.n3"; stevenh@67: stevenh@67: public void run(String[] args) { stevenh@67: stevenh@67: // If a command-line argument was supplied, assume it's the path stevenh@67: // of an N3 ontology file stevenh@67: if (args.length == 1) stevenh@67: ontology = args[0]; steve@0: stevenh@67: OntModel ontModel = ModelFactory.createOntologyModel(OntModelSpec.OWL_MEM); stevenh@67: ontModel.read(ontology, "N3"); stevenh@67: steve@0: // Create custom sia Datapoint objects steve@0: List datapoints = SiaDatapointFactory.create(ontModel); stevenh@5: stevenh@13: // STEP 1 - Order the datapoints steve@0: Collections.sort(datapoints); stevenh@5: stevenh@86: // Add datapoint order info stevenh@86: SiaDatapointFactory.assertOrder(datapoints); stevenh@43: stevenh@86: // STEP 2 - Compute the SIA vector table stevenh@86: VectorTable vectorTableW = null; stevenh@86: try { stevenh@86: vectorTableW = SiaVectorTableElementFactory.createW(datapoints); stevenh@86: } catch (DimensionException e) { stevenh@86: e.printStackTrace(); stevenh@86: System.exit(-1); stevenh@86: } stevenh@67: stevenh@67: // STEP 3 - Create custom SIATEC VectorTableElement objects (V) stevenh@86: VectorTable vectorTableV = null; stevenh@86: try { stevenh@86: vectorTableV = SiaVectorTableElementFactory.createV(datapoints); stevenh@86: } catch (DimensionException e) { stevenh@86: e.printStackTrace(); stevenh@86: System.exit(-1); stevenh@86: } stevenh@67: List vteListV = vectorTableV.getVteList(); stevenh@5: stevenh@86: // STEP 4 - Order the VectorTableElement objects stevenh@67: Collections.sort(vteListV); steve@0: stevenh@86: // STEP 5 - Display the SIA (MTP) results stevenh@86: displaySiaResults(vteListV); steve@0: stevenh@86: // STEP 6 - "Vectorize" the MTPs stevenh@67: int m = vteListV.size(); stevenh@67: int i = 0; stevenh@67: ArrayList x = new ArrayList(); stevenh@67: stevenh@67: while (i < m) stevenh@67: { stevenh@67: ArrayList q = new ArrayList(); stevenh@67: int j = i + 1; stevenh@67: while (j < m && (vteListV.get(i).compareToIgnoreDatapoints(vteListV.get(j)) == 0)) stevenh@67: { stevenh@67: NDimensionalObject vector = vteListV.get(j).getFromDatapoint().subtract(vteListV.get(j - 1).getFromDatapoint()); stevenh@67: q.add(vector); stevenh@67: j++; stevenh@67: } stevenh@67: stevenh@67: SiatecX iq = new SiatecX(); stevenh@67: iq.setI(i+1); stevenh@67: iq.setQ(q); stevenh@67: x.add(iq); stevenh@67: i = j; stevenh@67: } stevenh@67: stevenh@67: // Sort the elements of x stevenh@67: Collections.sort(x); stevenh@67: stevenh@67: // Rename as y to match algorithm description in paper stevenh@67: ArrayList y = (ArrayList) x.clone(); stevenh@67: stevenh@86: // Display results using algorithm figures 23, 24 and 25 of the research paper stevenh@85: int countTecs = 0; stevenh@67: stevenh@67: int r = y.size(); stevenh@67: m = vteListV.size(); stevenh@67: i = 0; stevenh@67: System.out.println(); stevenh@67: System.out.print("{"); stevenh@67: if (r > 0) stevenh@67: { stevenh@67: do stevenh@67: { stevenh@67: int j = y.get(i).getI() - 1; stevenh@67: List iList = new ArrayList(); stevenh@67: while (j < m && (vteListV.get(j).compareToIgnoreDatapoints(vteListV.get(y.get(i).getI() - 1)) == 0)) stevenh@67: { stevenh@67: iList.add(vteListV.get(j).getFromDatapoint().getOrderedIndex()); stevenh@67: j++; stevenh@67: } stevenh@85: countTecs++; stevenh@67: System.out.print("<"); stevenh@67: Display.printPattern(iList, datapoints); stevenh@67: stevenh@67: System.out.print(","); stevenh@67: printSetOfTranslators(iList, datapoints, vectorTableW); stevenh@67: System.out.print(">"); stevenh@67: do stevenh@67: { stevenh@67: i++; stevenh@67: } while (i < r && (y.get(i).compareToIgnoreI(y.get(i - 1)) == 0)); stevenh@67: stevenh@67: if (i < r) stevenh@67: { stevenh@67: System.out.print(","); stevenh@67: System.out.println(); stevenh@67: } stevenh@67: } while (i < r); stevenh@67: } stevenh@67: System.out.println("}"); stevenh@43: stevenh@85: System.out.println("Number of TECs: " + countTecs); stevenh@67: System.out.println("Number of Datapoints (n) = " + datapoints.size() + ", k = 3"); stevenh@5: } stevenh@5: stevenh@5: /** stevenh@5: * @param vteList stevenh@5: */ stevenh@86: public void displaySiaResults(List vteList) { stevenh@5: int m = vteList.size(); stevenh@5: int i = 0; stevenh@5: stevenh@5: System.out.println(); stevenh@5: System.out.print("{"); stevenh@5: stevenh@85: int countMtps = 0; stevenh@5: while (i < m) stevenh@5: { stevenh@85: countMtps++; stevenh@5: System.out.print("<"); stevenh@13: Display.printVector(vteList.get(i)); stevenh@67: stevenh@5: System.out.print(",{"); stevenh@13: Display.printVector(vteList.get(i).getFromDatapoint()); stevenh@67: stevenh@5: int j = i + 1; stevenh@5: stevenh@5: while (j < m && (vteList.get(i).compareToIgnoreDatapoints(vteList.get(j)) == 0)) stevenh@5: { stevenh@5: System.out.print(","); stevenh@13: Display.printVector(vteList.get(j).getFromDatapoint()); stevenh@5: j++; stevenh@5: } stevenh@5: System.out.print("}>"); stevenh@5: if (j < m) stevenh@5: { stevenh@5: System.out.print(","); stevenh@5: System.out.println(); stevenh@5: } stevenh@5: i = j; stevenh@5: } stevenh@5: System.out.println("}"); stevenh@85: System.out.println("Number of MTPs: " + countMtps); stevenh@5: } stevenh@5: stevenh@5: /** stevenh@5: * @param vteIter stevenh@5: * @param message stevenh@5: */ stevenh@5: public void displayNDimensionalObjects(Iterator vteIter, String message) { stevenh@5: System.out.println(message); stevenh@5: System.out.println("----------"); stevenh@5: while (vteIter.hasNext()) stevenh@5: { stevenh@5: VectorTableElement vte = vteIter.next(); stevenh@5: System.out.println("from: " + vte.getFromDatapoint().getResource().getLocalName() + " to: " + vte.getToDatapoint().getResource().getLocalName()); steve@0: } steve@0: } steve@0: stevenh@5: /** stevenh@5: * @param datapointIter stevenh@5: * @param message stevenh@5: */ stevenh@5: public void displayDatapoints(Iterator datapointIter, String message) { stevenh@5: System.out.println(message); stevenh@5: System.out.println("----------"); stevenh@5: while (datapointIter.hasNext()) stevenh@5: { stevenh@5: Datapoint datapoint = datapointIter.next(); stevenh@5: System.out.println( datapoint.getResource().getLocalName()); stevenh@5: } stevenh@5: } stevenh@5: stevenh@67: private void printSetOfTranslators(List iList, List datapoints, VectorTable vectorTableW) { stevenh@67: int p = iList.size(); stevenh@67: int n = datapoints.size(); stevenh@67: stevenh@67: if (p == 1) stevenh@67: { stevenh@67: System.out.print("{"); stevenh@67: Display.printVector(vectorTableW.getVector(iList.get(0), 1)); stevenh@67: for (int k = 2; k <= n; k++) stevenh@67: { stevenh@67: System.out.print(","); stevenh@67: Display.printVector(vectorTableW.getVector(iList.get(0), k)); stevenh@67: } stevenh@67: System.out.print("}"); stevenh@67: } stevenh@67: else stevenh@67: { stevenh@67: System.out.print("{"); stevenh@67: List jList = new ArrayList(); stevenh@67: for (int k = 0; k < p; k++) stevenh@67: { stevenh@67: jList.add(1); stevenh@67: } stevenh@67: boolean finished = false; stevenh@67: boolean first_vector = true; stevenh@67: int k = 1; stevenh@67: stevenh@67: while (!finished) stevenh@67: { stevenh@67: if (jList.get(k) <= jList.get(k - 1)) stevenh@67: { stevenh@67: jList.set(k, jList.get(k - 1) + 1); stevenh@67: } stevenh@67: stevenh@67: while (jList.get(k) <= (n - p + k + 1) stevenh@67: && (((VectorTableElement)vectorTableW.getVector(iList.get(k), jList.get(k))).compareToIgnoreDatapoints(((VectorTableElement)vectorTableW.getVector(iList.get(k - 1), jList.get(k - 1)))) < 0)) stevenh@67: { stevenh@67: jList.set(k, jList.get(k) + 1); stevenh@67: } stevenh@67: stevenh@67: if (jList.get(k) > n - p + k + 1) stevenh@67: { stevenh@67: finished = true; stevenh@67: } stevenh@67: else if (((VectorTableElement)vectorTableW.getVector(iList.get(k), jList.get(k))).compareToIgnoreDatapoints(((VectorTableElement)vectorTableW.getVector(iList.get(k - 1), jList.get(k - 1)))) > 0) stevenh@67: { stevenh@67: k = 1; stevenh@67: jList.set(0, jList.get(0) + 1); stevenh@67: if (jList.get(0) > n - p + 1) stevenh@67: { stevenh@67: finished = true; stevenh@67: } stevenh@67: } stevenh@67: else if (k + 1 == p) stevenh@67: { stevenh@67: if (!first_vector) stevenh@67: { stevenh@67: System.out.print(","); stevenh@67: } stevenh@67: else stevenh@67: { stevenh@67: first_vector = false; stevenh@67: } stevenh@67: stevenh@67: Display.printVector(vectorTableW.getVector(iList.get(k), jList.get(k))); stevenh@67: k = 0; stevenh@67: stevenh@67: while (k < p) stevenh@67: { stevenh@67: jList.set(k, jList.get(k) + 1); stevenh@67: if (jList.get(k) > n - p + k +1) stevenh@67: { stevenh@67: finished = true; stevenh@67: k = p -1; stevenh@67: } stevenh@67: k++; stevenh@67: } stevenh@67: k = 1; stevenh@67: } stevenh@67: else stevenh@67: { stevenh@67: k++; stevenh@67: } stevenh@67: } stevenh@67: System.out.print("}"); stevenh@67: } stevenh@67: } stevenh@67: stevenh@67: private void printX(ArrayList x) { stevenh@67: for (SiatecX iq : x) stevenh@67: { stevenh@67: System.out.print(iq.getI() + ","); stevenh@67: for (NDimensionalObject q : iq.getQ()) stevenh@67: { stevenh@67: System.out.print("<"); stevenh@67: int dimensions = q.getDimensionValues().size(); stevenh@67: for (int dim = 1; dim <= dimensions; dim++) stevenh@67: { stevenh@67: try { stevenh@67: System.out.print(q.getDimensionValue(dim) + (dim == dimensions ? "" : ",")); stevenh@67: } catch (DimensionException e) { stevenh@67: e.printStackTrace(); stevenh@67: System.exit(1); stevenh@67: } stevenh@67: } stevenh@67: System.out.println(">"); stevenh@67: } stevenh@67: System.out.println(); stevenh@67: } stevenh@67: } stevenh@67: stevenh@5: /** stevenh@5: * @param args stevenh@5: */ steve@0: public static void main(String[] args) { stevenh@43: long startTime = System.currentTimeMillis(); steve@0: SiaMain app = new SiaMain(); stevenh@67: app.run(args); stevenh@43: long endTime = System.currentTimeMillis(); stevenh@43: long elapsedTime = endTime - startTime; stevenh@43: System.out.println("Completed in " + elapsedTime + " ms"); steve@0: } steve@0: steve@0: }