I'm trying to ensure the JFrame remains responsive while updating the GUI. I'm using SwingWorker for this. The scenario is during the sequential flow of the program the following code gets executed.
public int[][] readInputFile(MatrixOperations matrixOperations,
String inputFile, Boolean isDirected) throws IOException {
List<String> fileLines = Files.readAllLines(Paths.get(inputFile),
StandardCharsets.UTF_8);
int[][] adjacencyMatrix = matrixOperations.createAdjacencyMatrixFromFile(
fileLines, isDirected);
//The following two lines perform the computationally expensive operation.
//So I'm asking SwingWorker to do this.
task = new Task(fileLines, isDirected, ROOT_GRAPH);
task.execute();
return adjacencyMatrix;
}
This is the SwingWorker class that is getting executed. The problem I'm facing is during the execution of for-loop within doInBackground(). The three functions namely createNodeFromFile(source), createNodeFromFile(destination),createEdgeFromFile(source, destination, isDirected) are being called in their own order during the execution of doInBackground() but they should be called sequentially. As a result I'm getting ConcurrentModification Exception or sometimes Node does not exist exception ( This is Graphstream library specific exception ). How do I resolve this?
import java.util.List;
import javax.swing.SwingWorker;
import org.graphstream.graph.Graph;
public class Task extends SwingWorker<Void, Integer>{
List<String> list;
Boolean isDirected;
Graph graph;
public Task(List<String> list, Boolean isDirected, Graph graph){
this.list = list;
this.isDirected = isDirected;
this.graph = graph;
}
#Override
public Void doInBackground() throws Exception {
// TODO Auto-generated method stub
int count = 0;
for (int i = 0; i < list.size(); i++) {
// System.out.println(fileContent.get(i));
if ((!list.get(i).startsWith("#"))
&& (list.get(i).length() > 1)) {
count++;
String[] arrLine = list.get(i).trim().split("\\s+");
String source = arrLine[0].trim();
String destination = arrLine[1].trim();
createNodeFromFile(source);
createNodeFromFile(destination);
createEdgeFromFile(source, destination, isDirected);
}
if (count % 1000 == 0) {
System.out.println("Finished processing " + count + " lines");
}
}
return null;
}
public void createNodeFromFile(String nodeId) {
if (graph.getNode(nodeId) == null) {
graph.addNode(nodeId);
showLabelOnRootGraph(nodeId, nodeId);
}
}
public void showLabelOnRootGraph(String nodeId, String label) {
graph.getNode(nodeId).addAttribute("ui.label", label);
}
public void createEdgeFromFile(String source, String destination, Boolean isDirected) {
if (graph.getNode(source).hasEdgeBetween(destination) == false) {
graph.addEdge("S" + source + "D" + destination, source,
destination, isDirected);
}
}
}
I found the answer to this. Basically, we have to return the object Graph from Swing Worker. This object has to be then passed to process(). Here is the solution:
package main.graph.generate;
import java.util.Iterator;
import java.util.List;
import javax.swing.SwingWorker;
import org.graphstream.graph.Graph;
import org.graphstream.ui.view.Viewer;
import org.graphstream.ui.view.ViewerPipe;
public class Task extends SwingWorker<Graph, Graph>{
List<String> list;
Boolean isDirected;
Graph graph;
ViewerPipe viewerPipe;
public Task(List<String> list, Boolean isDirected, Graph graph, ViewerPipe viewerPipe){
this.list = list;
this.isDirected = isDirected;
this.graph = graph;
this.viewerPipe = viewerPipe;
}
#Override
public Graph doInBackground() throws Exception {
// TODO Auto-generated method stub
int count = 0;
//for (int i = 0; i < list.size(); i++) {
// System.out.println(fileContent.get(i));
for(Iterator it = list.iterator();it.hasNext();){
String line = (String) it.next();
if ((!line.startsWith("#"))
&& (line.length() > 1)) {
count++;
String[] arrLine = line.trim().split("\\s+");
String source = arrLine[0].trim();
String destination = arrLine[1].trim();
createNodeFromFile(source);
createNodeFromFile(destination);
createEdgeFromFile(source, destination, isDirected);
publish(graph);
}
if (count % 1000 == 0) {
System.out.println("Finished processing " + count + " lines");
}
}
return graph;
}
#Override
protected void process(List<Graph> graphs){
GraphGenerate.ROOT_GRAPH = graphs.get(graphs.size()-1);
viewerPipe.addAttributeSink(GraphGenerate.ROOT_GRAPH);
}
public void createNodeFromFile(String nodeId) {
if (graph.getNode(nodeId) == null) {
graph.addNode(nodeId);
showLabelOnRootGraph(nodeId, nodeId);
}
}
public void showLabelOnRootGraph(String nodeId, String label) {
graph.getNode(nodeId).addAttribute("ui.label", label);
}
public void createEdgeFromFile(String source, String destination, Boolean isDirected) {
if (graph.getNode(source).hasEdgeBetween(destination) == false) {
graph.addEdge("S" + source + "D" + destination, source,
destination, isDirected);
}
}
}
Cheers!
Related
I'm trying to modify Dijkstra's algorithm to show all the paths that have the minimum value. So I decided to use a list of previous vertices. And I added an if clause that checks if the path is igual to the previous with minimum value I add the previous vertex as the parent of the current one.
The problem is that I am getting a StackOverflow error and I don't know what is causing it.
This is my code:
The purpose of the code below is to calculate Dijkstra for all of the vertices in the graph, calculate the number of times a vertex appears in the minimum paths found and display in decrescent order the all of them.
public class Dijkstra {
public static final Map<String, Integer> ordem = new HashMap<>();
public static void main(String[] args) throws FileNotFoundException, IOException {
List<Graph.Edge> edges = new ArrayList<>();
try {
FileReader arq = new FileReader("input.txt");
BufferedReader fw = new BufferedReader(arq);
String linha = "";
while (fw.ready()) {
linha = fw.readLine();
if (!linha.equals("0,0,0")) {
String parts[] = linha.split(",");
ordem.put(parts[0], 0);
ordem.put(parts[1], 0);
Graph.Edge a = new Graph.Edge(parts[0], parts[1], 100 - Integer.parseInt(parts[2]));
edges.add(a);
} else {
break;
}
}
fw.close();
} catch (FileNotFoundException e) {
e.printStackTrace();
}
Graph g = new Graph(edges);
for (int i = 0; i < 5; i++) {
g.dijkstra(String.valueOf(i));
g.printAllPaths();
}
Object[] a = ordem.entrySet().toArray();
Arrays.sort(a, new Comparator() {
public int compare(Object o1, Object o2) {
return ((Map.Entry<String, Integer>) o2).getValue()
.compareTo(((Map.Entry<String, Integer>) o1).getValue());
}
});
for (Object e : a) {
System.out.print(((Map.Entry<String, Integer>) e).getKey() + " ");
}
System.out.println("\n");
}
}
class Graph {
private final Map<String, Vertex> graph;
public static class Edge {
public final String v1, v2;
public final int dist;
public Edge(String v1, String v2, int dist) {
this.v1 = v1;
this.v2 = v2;
this.dist = dist;
}
}
public static class Vertex implements Comparable<Vertex> {
public final String name;
public int dist = Integer.MAX_VALUE;
public List<Vertex> previous = new ArrayList<>();
public final Map<Vertex, Integer> neighbours = new HashMap<>();
public Vertex(String name) {
this.name = name;
}
private void printPath() {
if (this == this.previous) {
} else if (this.previous == null) {
} else {
//This is where I am getting the error
for (int i = 0; i<this.previous.size(); i++){
this.previous.get(i).printPath();
Dijkstra.ordem.replace(this.name, Dijkstra.ordem.get(this.name) + 1);
}
}
}
public int compareTo(Vertex other) {
if (dist == other.dist) {
return name.compareTo(other.name);
}
return Integer.compare(dist, other.dist);
}
#Override
public String toString() {
return "(" + name + ", " + dist + ")";
}
}
public Graph(List<Graph.Edge> edges) {
graph = new HashMap<>(edges.size());
for (Edge e : edges) {
if (!graph.containsKey(e.v1)) {
graph.put(e.v1, new Vertex(e.v1));
}
if (!graph.containsKey(e.v2)) {
graph.put(e.v2, new Vertex(e.v2));
}
}
for (Edge e : edges) {
graph.get(e.v1).neighbours.put(graph.get(e.v2), e.dist);
graph.get(e.v2).neighbours.put(graph.get(e.v1), e.dist);
}
}
public void dijkstra(String startName) {
if (!graph.containsKey(startName)) {
System.err.printf("Graph doesn't contain start vertex \"%s\"\n", startName);
return;
}
final Vertex source = graph.get(startName);
NavigableSet<Vertex> q = new TreeSet<>();
// Inicializacao dos vertices
for (Vertex v : graph.values()) {
//v.previous = v == source ? list : null;
if (v == source) {
v.previous.add(source);
} else {
v.previous = new ArrayList<>();
}
v.dist = v == source ? 0 : Integer.MAX_VALUE;
q.add(v);
}
dijkstra(q);
}
private void dijkstra(final NavigableSet<Vertex> q) {
Vertex u, v;
while (!q.isEmpty()) {
u = q.pollFirst();
if (u.dist == Integer.MAX_VALUE) {
}
for (Map.Entry<Vertex, Integer> a : u.neighbours.entrySet()) {
v = a.getKey();
final int alternateDist = u.dist + a.getValue();
if (alternateDist < v.dist) {
q.remove(v);
v.dist = alternateDist;
v.previous.add(u);
q.add(v);
} else if(alternateDist == v.dist) {
v.previous.add(u);
}
}
}
}
public void printPath(String endName) {
if (!graph.containsKey(endName)) {
System.err.printf("Graph doesn't contain end vertex \"%s\"\n", endName);
return;
}
graph.get(endName).printPath();
//System.out.println();
}
public void printAllPaths() {
for (Vertex v : graph.values()) {
v.printPath();
}
}
}
This is the error:
Exception in thread "main" java.lang.StackOverflowError
at Graph$Vertex.printPath(Dijkstra.java:117)
at Graph$Vertex.printPath(Dijkstra.java:118)
As the Error message already suggests: Your dijkstra isn't the problem.
The problem is printPath() calling itself.
Likely the culprit is
if (this == this.previous) {} ...
You compare Vertex this to List<Vertex> previous. Maybe you want to check
if (this == this.previous.get(this.previous.size() - 1)) {} ...
instead.
I didn't test this, because your code is (1.) too long and (2.) not self-contained (missing at least "input.txt").
I am currently working on a "code parser" parsing Valve Map Format (.vmf files) into a java readable Object.
In vmf files,
there are 2 types of objects: Classes and Properties.
classes have a name and can contain other classes and properties.
properties have a name and an unlimited number of values.
Therefore I created a VMFClass Object Class and a VMFProperty Object Class.
I created a List with self-created HierarchyObjects, containing the VMFClass/VMFProperty Object, an UUID and the parentUUID.
The VMFClass Object Contains 2 Lists one with sub-VMFClasses, one with properties.
My Problem is that I have no clue on how to achieve that a Class contains all of its subclasses, since I can't tell how much subclasses the subclasses have and so on...
Here is my Code (Github):
HierachyObject:
package net.minecraft.sourcecraftreloaded.utils;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;
public class HierarchyObject {
private static Map<Long, Long> usedUUIDs = new HashMap<>();
private long parentUUID;
private long UUID;
private Object object;
/**
*
* #param Object
* #param parent -1 is maximum level
*/
public HierarchyObject(Object object, long parent) {
this.object = object;
this.parentUUID = parent;
while (true) {
long random = (long) (Math.random() * Long.MAX_VALUE);
if (usedUUIDs.containsKey(random)) {
this.UUID = random;
usedUUIDs.put(random, parent);
break;
}
}
}
public long getUUID() {
return UUID;
}
public long getParentUUID() {
return parentUUID;
}
public static long getParentUUIDbyUUID(long UUID) {
if (usedUUIDs.containsKey(UUID)) {
return usedUUIDs.get(UUID);
}
return -1;
}
public Object getObject() {
return object;
}
public static boolean hasChild(long UUID){
if(usedUUIDs.containsValue(UUID)){
return true;
}
if(UUID == -1){
return true;
}
return false;
}
public boolean hasChild(){
return hasChild(this.UUID);
}
public static long[] getChildUUIDs(long UUID){
if(hasChild(UUID)){
List<Long> cUUIDs = new ArrayList<>();
for(int i = 0; i < usedUUIDs.size(); i++){
for (Map.Entry<Long, Long> e : usedUUIDs.entrySet()) {
if(e.getValue().longValue() == UUID){
cUUIDs.add(e.getKey());
}
}
}
return ListUtils.toPrimitivebyList(cUUIDs);
}
return null;
}
}
VMFProperty:
package net.minecraft.sourcecraftreloaded.source;
public class VMFProperty{
private String name;
private String[] values;
public VMFProperty(String name, String... values) {
this.name = name;
this.values = values;
}
public String getName() {
return name;
}
public String[] getValues() {
return values;
}
#Override
public boolean equals(Object paramObject){
if(paramObject instanceof VMFProperty){
return ((VMFProperty)paramObject).name.equals(this.name) && ((VMFProperty)paramObject).values.equals(this.values);
}
return false;
}
}
VMFClass:
package net.minecraft.sourcecraftreloaded.source;
import java.util.List;
public class VMFClass{
private List<VMFClass> classes;
private List<VMFProperty> properties;
private String name;
public VMFClass(String name, List<VMFClass> classes, List<VMFProperty> properties) {
this.name = name;
this.classes = classes;
this.properties = properties;
}
public String getName() {
return name;
}
public List<VMFClass> getClasses() {
return classes;
}
public List<VMFProperty> getProperties() {
return properties;
}
public void add(VMFClass vmfclass) {
classes.add(vmfclass);
}
public void add(VMFProperty vmfproperty) {
properties.add(vmfproperty);
}
public void remove(VMFClass vmfclass) {
classes.remove(vmfclass);
}
public void remove(VMFProperty vmfproperty) {
properties.remove(vmfproperty);
}
#Override
public boolean equals(Object paramObject){
if(paramObject instanceof VMFClass){
return ((VMFClass)paramObject).properties.equals(this.properties) && ((VMFClass)paramObject).classes.equals(this.classes) && ((VMFClass)paramObject).name.equals(this.name);
}
return false;
}
}
VMFObject (the class executing all the code):
package net.minecraft.sourcecraftreloaded.source;
import java.io.File;
import java.util.ArrayList;
import java.util.List;
import net.minecraft.sourcecraftreloaded.utils.HierarchyObject;
public class VMFObject {
private String rawfile = "";
private List<VMFClass> toplevelclasses;
private static final String INVALID_CHARS = "\\*,;<>|?=`´#'+~^°!§$%&()[].:-_";
public VMFObject(List<VMFClass> toplevelclasses) {
this.toplevelclasses = toplevelclasses;
}
public VMFObject() {
this(new ArrayList<VMFClass>());
}
public void write(File file) {
VMFWriter.write(file, rawfile);
}
public VMFObject read(File file) throws VMFParsingException {
this.rawfile = VMFReader.read(file);
parse();
return this;
}
public List<VMFClass> getClasses() {
return toplevelclasses;
}
private void parse() throws VMFParsingException {
evaluate();
get();
}
private void evaluate() throws VMFParsingException {
char[] textchars = rawfile.toCharArray();
int[] c = new int[]{0, 0, 0};
int line = 0;
int linepos = 0;
for (int i : textchars) {
linepos++;
if (textchars[i] == '\n') {
line++;
linepos = 0;
c[3] = 0;
if (c[3] % 2 != 0) {
throw new VMFParsingException("Invalid quotes on line" + line + ":" + linepos);
}
}
if (textchars[i] == '{') {
c[1]++;
}
if (textchars[i] == '}') {
c[2]++;
}
if (textchars[i] == '"') {
c[3]++;
if (c[1] - c[2] == 0) {
}
}
if (textchars[i] == '/' && textchars[i + 1] == '/') {
while (true) {
i++;
if (textchars[i] == '\n') {
break;
}
}
}
if (textchars[i] == '/' && textchars[i + 1] == ' ') {
throw new VMFParsingException("Invalid Character '/' on line" + line + ":" + linepos);
}
if (INVALID_CHARS.indexOf(textchars[i]) != -1) {
throw new VMFParsingException("Invalid Character '" + textchars[i] + "' on line" + line + ":" + linepos);
}
}
if (c[1] != c[2]) {
throw new VMFParsingException("Unbalanced brackets in vmf File");
}
}
public void add(VMFClass vmfclass) {
toplevelclasses.add(vmfclass);
}
private void get() throws VMFParsingException {
List<HierarchyObject> content = new ArrayList<>();
long curparent = -1;
String[] text = rawfile.split("\n");
for (int i = 0; i < text.length; i++) {
String line = text[i].trim();
if (line.startsWith("//")) {
continue;
} else {
byte quotec = 0;
char[] linechar = line.toCharArray();
boolean readp = false;
List<String> reads = new ArrayList<>();
byte creads = 0;
for (int y = 0; y < linechar.length; y++) {
if (linechar[y] == '/' && linechar[y + 1] == '/') {
break;
}
if (linechar[y] == '"') {
quotec++;
if (quotec % 2 == 0) {
readp = false;
creads++;
} else {
readp = true;
}
}
if (readp) {
reads.set(creads, reads.get(creads) + linechar[y]);
}
if (linechar[y] == '{') {
HierarchyObject object = new HierarchyObject(new VMFClass(line.substring(line.substring(0, y).lastIndexOf(' '), y).trim(), null, null), curparent);
content.add(object);
curparent = object.getUUID();
}
if (linechar[y] == '}') {
curparent = HierarchyObject.getParentUUIDbyUUID(curparent);
}
}
content.add(new HierarchyObject(new VMFProperty(reads.remove(0), reads.toArray(new String[reads.size()])), curparent));
}
}
buildObject(content);
}
private void buildObject(List<HierarchyObject> content) {
long curUUID = -1;
for(int i = 0; i < HierarchyObject.getChildUUIDs(curUUID).length; i++){
HierarchyObject.getChildUUIDs(curUUID);
}
//TODO implement
}
}
the //TODO part is where the Hierachy Object should get "converted" to the actual object.
Overview
It seems to me that your class layout is overcomplicated.
Let's try to simplify it...
What you have described with the VMF model is essentially a linked-list Tree.
Here's what the model looks like:
[.vmf file] (root)
/ \
_____/ \ _____
/ \
/ \
(VMFClass) (VMFClass)
/ \ / \
/ \ / \
/ \ / \
(VMFClass) (VMFProperties) (VMFClass) (VMFProperties)
/ \
/ \
/ \
(VMFClass) (VMFProperties)
What you need:
A Parser class (in your case, you have VMFObject, but lets call this class VMFParser).
The VMFClass and VMFProperty classes which you have are fine.
What you don't need:
The HierarchyObject class. The VMFParser can be the main controller and container for the hierarchy (e.g. the linked-list Tree model).
All the UUIDs (parent, child, etc.) These are just complicated things, but I see why you have them. You don't need them to track the hierarchy - Java will do this for us!!
VMFClass
public class VMFClass
{
// name of the class
private String name;
// reference back up to the parent
private VMFClass parentClass = null;
// all direct children go here
private List<VMFClass> children = new ArrayList<VMFClass>();
// I don't think you need a list of properties here since your VMFProperty class holds onto an array of properties
private VMFProperty properties;
// set the parent of this class
public void setParent (VMFClass parent)
{
this.parentClass = parent;
}
// get the direct children
public List<VMFClass> getChildren()
{
return this.children;
}
// rest of methods...
}
VMFParser
class VMFParser
{
private String rawfile = "";
// this is really the container for everything - think of it as the file shell
private VMFClass root = new VMFClass("root", null, null);
// construct yourself with the file
public VMFParser (String fileName)
{
this.rawfile = fileName;
}
public void parse ()
{
// all the parsing code goes here
read();
evaluate();
get();
// now at this point your hierarchy is built and stored in the
// root object in this class.
// Use the traverse method to go through it
}
private void get() throws VMFParsingException
{
// keep a reference to the current VMFClass parent
// starts out as root
VMFClass currParentClass = root;
// main parse loop
for (...)
{
// if you find a class
VMFClass currClass = new VMFClass(/* params here */);
// add this class to the parent
currParentClass.add(currClass);
// set the parent of this class
currClass.setParent(currParentClass);
// if you find a property
// parse and add all the properties to the property
VMFProperty property = new VMFProperty (/* value params here */);
// attach this property to the last VMF class that got parsed
currClass.setPoperties(property);
// If you nest deeper into classes, then the parent becomes the current class
currParentClass = currClass;
// If you go back out of a class
currParentClass = currClass.getParent();
}
}
// Traverse the hierarchy
public void traverse ()
{
traverseTree(root);
}
private void traverseTree (VMFClass root)
{
System.out.println("Class Name: " + root.getName());
// print out any properties
VMFProperty prop = root.getProperty();
if (prop != null)
{
System.out.println("Property Name: " + prop.getName());
String [] props = prop.getValues();
for (String s: props)
{
System.out.println("Value: " + s);
}
}
// get all child classes
List<VMFClass> children = root.getChildren();
for (VMFClass c: children)
{
traverseTree(c);
}
}
}
Client Code
Example
public static void main(String[] args)
{
VMFParser vmfParser = null;
try
{
vmfParser = new VMFParser("myFile.vmf");
vmfParser.parse();
// access the vmfParser for the hierarchy
vmfParser.traverse();
}
catch (VMFParsingException vpe)
{
// do something here
vpe.printStackTrace();
}
finally
{
// clean up...
}
}
If you are just looking to find all sub classes of particular class or interface , this might help you,
How can I get a list of all the implementations of an interface programmatically in Java?
I am working on a project with a datatructure that is deeper than 1 level and I try to box different user-defined datatypes to hold information of all levels.
First Level: A class that has only an ArrayList of level 2 datatype and some functions to access the data of all Levels.
Second Level: A class that has some standard variables and an ArrayList of Level 3 datatype and also some functions .
Third Level: A class / record of some standard variables
The instance of the first-level datatype should be used by more than one activity of my application (almost all).
Here is my problem: I can initialize the first-level and add some objects to the list, but I could not do so with the second level. If I add some object in the list of the second level all seems to be good, but when I access this data a NullPointerException occurs.
Here is my question: Is it possible to box datatypes in more than 1 level? And where I should search for the error.
For better understanding the sources:
modulData.java (First Level)
package de.myApp.dataholder;
import java.util.ArrayList;
import android.util.Log;
public class modulData {
// Constructor
private static final modulData mainModulDataHolder = new modulData();
public static modulData getInstance() {return mainModulDataHolder;}
// Data
private ArrayList<isModulData> mIsModulData;
// Functions
public void init() {
this.mIsModulData = new ArrayList<isModulData>();
}
public isModulData getModul(int mID) {
isModulData result = null;
int i;
for (i = 0; i < mIsModulData.size(); i++) {
if (mIsModulData.get(i).ID() == mID) {
result = mIsModulData.get(i);
break;
}
}
return result;
}
public isCatData getCategory(int mID, int cID) {
isCatData result = new isCatData();
isCatData buffer = new isCatData();
int i,j ;
for (i = 0; i < mIsModulData.size(); i++) {
if (mIsModulData.get(i).ID() == mID) {
for(j = 0; j < mIsModulData.get(i).CountCategorys(); j++) {
buffer = mIsModulData.get(i).getCategory(j);
if (buffer.ID() == cID) {
result = buffer;
break;
}
}
}
}
return result;
}
public int ModulCount() {
int result = 0;
if (mIsModulData != null) { result = mIsModulData.size(); }
return result;
}
public int CategoryCount(int mID) {
int result = -1;
int i;
for (i = 0; i < mIsModulData.size(); i++) {
if (mIsModulData.get(i).ID() == mID) {
result = mIsModulData.get(i).CountCategorys();
break;
}
}
return result;
}
public int addModulWithJSON(String jsonString) {
int result = -1;
isModulData newModul = new isModulData();
newModul.initCategorys();
if (mIsModulData == null) { this.init(); }
result = newModul.decodeFromJSON(jsonString);
mIsModulData.add(newModul);
return result;
}
public int addCategoryWithJSON(int mID, String jsonString) {
int result = -1;
int i;
for (i = 0; i < mIsModulData.size(); i++){
if (mIsModulData.get(i).ID() == mID) {
result = mIsModulData.get(i).addCategoryWithJSON(jsonString);
Log.i("AddCategoryWithJSON","Add Category "+ String.valueOf(result));
// Here is the Problem: Added but no access to Data. Null Object reference !!!!
Log.i("AddCategoryWithJSON", mIsModulData.get(mID).getCategory(result).Title());
break;
}
}
return result;
}
}
isModulData.java (second level)
package de.myApp.dataholder;
import java.util.ArrayList;
import org.json.JSONArray;
import org.json.JSONException;
import android.util.Log;
public class isModulData {
// Constructor
private static final isModulData modulDataHolder = new isModulData();
public static isModulData getInstance() {return modulDataHolder;}
// Data
private ArrayList<isCatData> mIsCatData;
private int mID;
private String mTitle;
private boolean misActive;
private int mBackgroundID;
// Functions
public int ID() { return this.mID; }
public String Title() { return this.mTitle; }
public boolean ActiveState() { return this.misActive; }
public int BackgroundID() { return this.mBackgroundID; }
public int decodeFromJSON(String jsonString) {
int result;
try {
JSONArray jArray = new JSONArray(jsonString);
this.mID = Integer.parseInt(jArray.getString(0).toString());
this.mTitle = jArray.getString(1).toString();
this.misActive = Boolean.parseBoolean(jArray.getString(2).toString());
this.mBackgroundID = Integer.parseInt(jArray.getString(3).toString());
result = this.mID;
} catch (JSONException e) {
e.printStackTrace();
Log.w("JSONDecode CMD801","Decode raised in JSONException ["+e.toString()+"]");
result = -1;
}
return result;
}
public int addCategoryWithJSON(String jsonString) {
int result = -1;
if (this.mIsCatData == null) { this.initCategorys(); }
isCatData cNewCategory = new isCatData();
result = cNewCategory.decodeFromJSON(jsonString);
this.mIsCatData.add(cNewCategory);
return result;
}
public isCatData getCategory(int cID) {
isCatData result = new isCatData();
if (cID < mIsCatData.size() -1) {
result = mIsCatData.get(cID);
} else {
result = null;
}
return result;
}
public void initCategorys() {
this.mIsCatData = new ArrayList<isCatData>();
}
public int CountCategorys() {
return this.mIsCatData.size();
}
}
isCatData.java (third level)
package de.myApp.dataholder;
import org.json.JSONArray;
import org.json.JSONException;
import android.util.Log;
public class isCatData {
// Constructor
private static final isCatData catDataHolder = new isCatData();
public static isCatData getInstance() {return catDataHolder;}
// Data
private int cID;
private String cTitle;
private boolean cisActive;
private boolean cisWriteEnable;
private int cBackgroundID;
// Functions
public int ID() { return this.cID; }
public String Title() { return this.cTitle; }
public boolean ActiveState() { return this.cisActive; }
public boolean WriteEnableState() { return this.cisWriteEnable; }
public int BackgroundID() { return this.cBackgroundID; }
public int decodeFromJSON(String jsonString) {
int result;
try {
JSONArray jArray = new JSONArray(jsonString);
this.cID = Integer.parseInt(jArray.getString(0).toString());
this.cTitle = jArray.getString(1).toString();
this.cisActive = Boolean.parseBoolean(jArray.getString(2).toString());
this.cisWriteEnable = Boolean.parseBoolean(jArray.getString(3).toString());
this.cBackgroundID = Integer.parseInt(jArray.getString(4).toString());
result = this.cID;
} catch (JSONException e) {
e.printStackTrace();
Log.w("JSONDecode CMD801","Decode raised in JSONException ["+e.toString()+"]");
result = -1;
}
return result;
}
}
I have this code and i want to implement a limit to the depth, how can i implement that here? Could i store the current depth somehow and compare it with the given limit? If so, how can i do that?
Thanks.
import java.util.List;
import java.util.ArrayList;
import java.util.Stack;
interface GoalFunction<T>
{
boolean evaluate(Vertex<T> o);
}
public class Vertex<T>
{
private final T data;
private final List<Vertex<T>> _successors = new ArrayList<Vertex<T>>();
Vertex(T data) { this.data = data; }
T getData() { return data; }
List<Vertex<T>> successors() { return _successors; }
public static <T> boolean depthFirstSearch(Vertex<T> start,
GoalFunction<T> isGoal,
Stack<Vertex<T>> result)
{
if (result.contains(start))
{
return false;
}
result.push(start);
if (isGoal.evaluate(start))
{
return true;
}
for (Vertex<T> v : start.successors()) {
if (depthFirstSearch(v, isGoal, result))
{
return true;
}
}
// No path was found
result.pop();
return false;
}
public static List<Vertex<Integer>> petersenGraph()
{
List<Vertex<Integer>> v = new ArrayList<Vertex<Integer>>();
for (int i = 0; i < 10; i++)
{
v.add(new Vertex<Integer>(i));
}
int[][] edges =
{{0,1}, {1,0}, {1,2}, {2,1}, {2,3}, {3,2}, {3,4}, {4,3}, {4,0}, {0,4},
{5,6}, {6,5}, {6,7}, {7,6}, {7,8}, {8,7}, {8,9}, {9,8}, {9,5}, {5,9},
{5,0}, {0,5}, {6,2}, {2,6}, {7,4}, {4,7}, {8,1}, {1,8}, {9,3}, {3,9}};
for (int[] e : edges)
{
v.get(e[0]).successors().add(v.get(e[1]));
}
return v;
}
public static void main(String[] args)
{
List<Vertex<Integer>> v = petersenGraph();
Stack<Vertex<Integer>> path = new Stack<Vertex<Integer>>();
if (depthFirstSearch(v.get(0), new GoalFunction<Integer>() {
public boolean evaluate(Vertex<Integer> v)
{
return v.getData() == 7;
}
}, path))
{
System.out.print("Found path: ");
for (Vertex<Integer> u : path)
{
System.out.print(u.getData() + " ");
}
System.out.println();
}
else
{
System.out.println("No path found");
}
}
}
Reimplement your DFS using recursion. Pass the incrementing value to the recursive function of the DFS:
void recursive(int depth, .. parameters) {
if (depth > CUT_OFF)
return;
..
recursive(depth+1, parameters1);
recursive(depth+1, parameters2);
}
Then you are aware about the current depth and can break it at any level.
In the following program I'm inserting
files[i].lastModified() value in allFiles HashMap in RThread class
when I tried to retrive the value of lastModified from allFiles HashMap in the main class the value is coming as null. So instead of lastModified value I placed File object directly in HashMpa then it worked.
Anyone guide me the concept behind this.
import java.io.File;
import java.util.ArrayList;
import java.util.Comparator;
import java.util.Iterator;
import java.util.List;
import java.util.Map;
import java.util.TreeMap;
import java.util.concurrent.ConcurrentHashMap;
public class RCFLister {
ConcurrentHashMap allFiles = new ConcurrentHashMap();
String fileType = null;
/**
* #param args
*/
public static void main(String[] args) {
RCFLister rcFileLister = new RCFLister();
rcFileLister.recentFiles(args);
}
public void recentFiles(String[] args) {
int days = 1;
ThreadGroup rootthreadGr = new ThreadGroup("rootsThreadGroup");
// reading number of days
if (args.length > 0 && args[0] != null) {
days = Integer.valueOf(args[0]);
}
// reading file type
if (args.length > 0 && args[0] != null) {
fileType = args[1];
}
fileType = "png";
// fileextFilter = new FileExtensionFilter(fileType);
File[] roots = File.listRoots();
List threads = new ArrayList();
for (int i = 0; i < roots.length; i++) {
// System.out.println(roots[i].getAbsolutePath());
// rfThread = null;
RThread rfThread = new RThread(roots[i]);
Thread t = new Thread(rfThread);
t.start();
threads.add(t);
}
for (int i = 0; i < threads.size(); i++) {
try {
((Thread) threads.get(i)).join();
} catch (InterruptedException e) {
// TODO Auto-generated catch block
e.printStackTrace();
}
}
ValueComparator vc = new ValueComparator(allFiles);
TreeMap sortedMap = new TreeMap(vc);
sortedMap.putAll(allFiles);
System.out.println(sortedMap.size());
Iterator it = sortedMap.keySet().iterator();
while (it.hasNext()) {
Object key = it.next();
System.out.println(key + " " + sortedMap.get(key));
}
}
private class ValueComparator implements Comparator {
Map allFiles;
public ValueComparator(Map allFiles) {
this.allFiles = allFiles;
}
public int compare(Object o1, Object o2) {
if (((Long) allFiles.get(o1)) >= ((Long) allFiles.get(o2))) {
return -1;
} else {
return 1;
}
}
}
private class RThread implements Runnable {
File rootFolder;
RThread(File root) {
rootFolder = root;
}
public void run() {
getFiles(rootFolder);
}
public void getFiles(File folder) {
File[] files = folder.listFiles();
for (int i = 0; files != null && i < files.length; i++) {
// System.out.println(files[i].getAbsolutePath());
if (files[i].isDirectory()) {
getFiles(files[i]);
} else if (fileType == null
|| (fileType != null && files[i].getName().endsWith(
fileType))) {
String filename = null;
try {
filename = files[i].getCanonicalPath();
} catch (Exception e) {
e.printStackTrace();
}
if(files[i].lastModified()!=0)
allFiles.put(filename, files[i].lastModified());
}
}
}
}
}
compare() method of ValueComparator never returns 0. Return 0 means equality which is missing so even if key is present it is not found.
Also the key is String(filename) and you are comparing by value (long). Need to rethink how you want to store data.
Just to make sure it is only problem, print CocurrentHashMap.
Do use Generic, it looks tedious at beginning but is really not that bad. It will help to compiler code without warning and achieve type safety.