jGraphT - Remove a vertex and reconnect all vertices which were connected to the removed one - jgrapht

I`m new to graphs and fiddling around with JGraphT at the moment. I have a simple graph where I want to remove a certain vertex. Removing is no problem at all but I need to reconnect all the vertices which were connected with the removed one.
See this example graph:
SimpleDirectedGraph<String, DefaultEdge> g = new SimpleDirectedGraph<>(DefaultEdge.class);
g.addVertex("Level 1");
g.addVertex("Level 2.1");
g.addVertex("Level 2.2");
g.addVertex("Level 3.1");
g.addVertex("Level 3.2");
g.addVertex("Level 3.3");
g.addVertex("Level 3.4");
g.addEdge("Level 1", "Level 2.1");
g.addEdge("Level 1", "Level 2.2");
g.addEdge("Level 2.1", "Level 3.1");
g.addEdge("Level 2.1", "Level 3.2");
g.addEdge("Level 2.1", "Level 3.3");
g.addEdge("Level 2.2", "Level 3.4");
How do I remove the vertex "Level 2.1" and reconnect the vertices of level 3 with the one of level 1. I could surely implement something on my own. But I think JGraphT will offer a more convienent way to do this. In the end I want to transform the mentioned graph into this one in an easy manner. (My real use cases are much more complex)
SimpleDirectedGraph<String, DefaultEdge> g = new SimpleDirectedGraph<>(DefaultEdge.class);
g.addVertex("Level 1");
g.addVertex("Level 2.2");
g.addVertex("Level 3.1");
g.addVertex("Level 3.2");
g.addVertex("Level 3.3");
g.addVertex("Level 3.4");
g.addEdge("Level 1", "Level 2.2");
g.addEdge("Level 1", "Level 3.1");
g.addEdge("Level 1", "Level 3.2");
g.addEdge("Level 1", "Level 3.3");
g.addEdge("Level 2.2", "Level 3.4");
I hope someone has the right hint for me. Thanks in advance.

The graph you provided as input is a tree graph. The general procedure would be to:
Store the predecessor vertices of the vertex you want to remove
Store the successor vertices of the vertex you want to remove
Remove the vertex, and reconnect all predecessors to all successors.
The code to accomplish this:
//Create the graph
Graph<String, DefaultEdge> g = new SimpleDirectedGraph<>(DefaultEdge.class);
g.addVertex("Level 1");
g.addVertex("Level 2.1");
g.addVertex("Level 2.2");
g.addVertex("Level 3.1");
g.addVertex("Level 3.2");
g.addVertex("Level 3.3");
g.addVertex("Level 3.4");
g.addEdge("Level 1", "Level 2.1");
g.addEdge("Level 1", "Level 2.2");
g.addEdge("Level 2.1", "Level 3.1");
g.addEdge("Level 2.1", "Level 3.2");
g.addEdge("Level 2.1", "Level 3.3");
g.addEdge("Level 2.2", "Level 3.4");
String vertex="Level 2.1"; //Vertex to be removed
//Get predecessors of the vertex that you want to delete:
List<String> pre = Graphs.predecessorListOf(g, vertex);
//Get successors of vertex that you want to delete:
List<String> suc = Graphs.successorListOf(g, vertex);
//Remove the vertex
g.removeVertex(vertex);
//Reconnect all vertices in the pre list to all vertices in the suc list.
for(String v1 : pre)
for(String v2 : suc)
g.addEdge(v1,v2);
System.out.println(g);
The output:
([Level 1, Level 2.2, Level 3.1, Level 3.2, Level 3.3, Level 3.4], [(Level 1,Level 2.2), (Level 2.2,Level 3.4), (Level 1,Level 3.1), (Level 1,Level 3.2), (Level 1,Level 3.3)])
Note that the above procedure does not preserve the edge objects. It simply re-connects the graph by creating new edges. If you want to preserve the edge objects, you must also store these prior to removal of the vertex. You can query the edges through g.outgoingEdgesOf(vertex).

Related

JFreeChart using Large Numbers as Values

I am currently working on a project using JFreeChart. I got everything working except when I start using large numbers, it goes all funny.
DefaultCategoryDataset dataset = new DefaultCategoryDataset();
dataset.addValue(1000, "Cars", "2015");
dataset.addValue(5000, "Bikes", "2015");
return dataset;
Output from above works perfect, but when I do this:
DefaultCategoryDataset dataset = new DefaultCategoryDataset();
dataset.addValue(999999999, "Cars", "2015");
dataset.addValue(999999999, "Bikes", "2015");
return dataset;
The 999999999 is converted to something like 1E7, 2E7, etc, etc.
How do I format it to show correctly?
This is my chart code.
JFreeChart chart = ChartFactory.createBarChart3D("My Title", "", "", catdata, PlotOrientation.VERTICAL, true, true, false);
BufferedImage bufferedImage = chart.createBufferedImage(780, 170, BufferedImage.TYPE_INT_RGB, null);
ImageIO.write(bufferedImage, "jpeg", out);
Any help will be much appreciated.
Thanks
You can use setNumberFormatOverride() and pass in a suitable NumberFormat. Hover over any bar to see the exact value in a tool tip.
NumberAxis rangeAxis = (NumberAxis) plot.getRangeAxis();
NumberFormat formatter = NumberFormat.getIntegerInstance();
rangeAxis.setNumberFormatOverride(formatter);

Lucene Index grown too large

I have a Lucene Index .FDT file that is about 5GB. I add records to it very often(1000 records per day) and none will be deleted. It has 5 fields and only one of them is text content of html page. I also run a query parser on this index to look for some keywords. Even though the index is optimized every time I insert, it is taking almost a minute to find the keyword in the text content of html page. Has anyone gone through this problem and any suggestions on how to resolve this?
These are the following steps that I do in my code
1.
Using SQLData Reader, get contents of table which contains title,EmployeeID,headline(short description of employee department), Date(date this employee was added to the table or his info changed), data (html version of employee details)
2. For each record in table do the following
string body= strip text from html from webpage or data;
var doc = new Document();
doc.Add(new Field("title", staticname, Field.Store.YES, Field.Index.ANALYZED)); //title is always "Employee info"
doc.Add(new Field("Employeeid", keyid.Replace(",", " "), Field.Store.YES, Field.Index.ANALYZED));
doc.Add(new Field("headline", head, Field.Store.YES, Field.Index.ANALYZED));
doc.Add(new Field("date", DateTools.DateToString(date, DateTools.Resolution.SECOND), Field.Store.YES, Field.Index.NOT_ANALYZED));
if (data == null)
data = "";
else if (data.Length > 500)
{
data = data.Substring(0, 500);
}
doc.Add(new Field("body", data, Field.Store.YES, Field.Index.ANALYZED));
indexWriter.AddDocument(doc);
indexWriter.Optimize();
indexWriter.Commit();
indexWriter.Dispose();
----In the search program
string searchword="disability";
QueryParser queryParser = new QueryParser(VERSION, "body", analyzer);
string word = "+Employeeid:" + Employeeid+ " +body:" + searchword;
Query query = queryParser.Parse(word);
try
{
IndexReader reader = IndexReader.Open(luceneIndexDirectory, true);
Searcher indexSearch = new IndexSearcher(reader);
TopDocs hits = indexSearch.Search(query, 1);
if (hits.TotalHits > 0)
{
float score = hits.ScoreDocs[0].Score;
if (score > MINSCORE)
{
results.Add(result); //it is a list that has EmployeeID,searchwordID,searchword,score
}
}
indexSearch.Dispose();
reader.Dispose();
indexWriter.Dispose();
}
Any input is appreciated.
Thanks
M
Do not store the body and headline field to your index.
doc.Add(new Field("headline", head, Field.Store.No, Field.Index.ANALYZED));
doc.Add(new Field("body", head, Field.Store.No, Field.Index.ANALYZED));
It is useless for search.

JFreeChart: move column labels upper

As I showed in the picture, I want to move the column labels (values 434, 2562, ....) a little upper. Is there any way to configure that?
MY initial problem was that due to the differences between columns, the labels on the last 2 columns are not visible anymore (they are actually 15 and 24 or stg like that). I dont know how to change that.
Thank you
You can use BarRenderer3D.setSeriesPositiveItemLabelPosition.
For example :
DefaultCategoryDataset dataset = new DefaultCategoryDataset();
dataset.addValue(51.0, "Series 1", "key1");
dataset.addValue(44.3, "Series 1", "key2");
// create the chart...
JFreeChart chart = ChartFactory.createBarChart3D("Demo","Category","Value",dataset,PlotOrientation.VERTICAL,false,true,false);
CategoryPlot plot = chart.getCategoryPlot();
CategoryAxis domainAxis = plot.getDomainAxis();
domainAxis.setVisible(false);
NumberAxis rangeAxis = (NumberAxis) plot.getRangeAxis();
rangeAxis.setUpperMargin(0.15);
BarRenderer3D renderer = (BarRenderer3D) plot.getRenderer();
CategoryItemLabelGenerator generator = new StandardCategoryItemLabelGenerator();
renderer.setSeriesItemLabelGenerator(0, generator);
renderer.setSeriesItemLabelsVisible(0, true);
renderer.setSeriesPositiveItemLabelPosition(0, new ItemLabelPosition(ItemLabelAnchor.OUTSIDE12,TextAnchor.BASELINE_CENTER));
renderer.setItemLabelAnchorOffset(10);
The result is :
CategoryPlot plot = (CategoryPlot) chart.getPlot();
BarRenderer renderer = (BarRenderer) plot.getRenderer();
renderer.setBasePositiveItemLabelPosition(new ItemLabelPosition(ItemLabelAnchor.OUTSIDE12, TextAnchor.TOP_CENTER,TextAnchor.HALF_ASCENT_CENTER,0D));

Jfree Using custom names to categories

I'm very new to Jfreechart, Please help me to get the solution for this, I'm using jfree to draw a graph for a categories which has specific code names like 563,258.855,etc... So i want to assign these values as labels to the domain axis, but by default it is assigning value1,value2,value3,etc... to categories.
But I wan to make it something like below
and here is my code,
final CategoryDataset dataset1 = DatasetUtilities.createCategoryDataset("Month to Date Occurences","value", data);
JFreeChart dualchart = ChartFactory.createBarChart(
"Top Ten Diagnostic Occurences", // chart title
"Category", // domain axis label
"Score", // range axis label
dataset1, // data
PlotOrientation.HORIZONTAL, // orientation
true, // include legend
true,
false
);
CategoryPlot plot = dualchart.getCategoryPlot();
plot.setRangeAxisLocation(AxisLocation.BOTTOM_OR_LEFT);
plot.setBackgroundPaint(Color.WHITE);
plot.setRangeGridlinePaint(Color.black);
BarRenderer renderer= (BarRenderer) plot.getRenderer();
renderer.setItemMargin(0.0);
CategoryAxis domainAxis = plot.getDomainAxis ();
domainAxis.setCategoryMargin(0.30); //distance between series
NumberAxis rangeAxis = (NumberAxis) plot.getRangeAxis();
rangeAxis.setRange(0.0, 100.0);
rangeAxis.setStandardTickUnits(NumberAxis.createIntegerTickUnits());
return dualchart;
Your suggestions are most welcome,
Thanks in advance.
You haven't included the code for dataset1 so it's hard to tell what the problem is but if you use something like this:
private static CategoryDataset createDataset() {
DefaultCategoryDataset dataset = new DefaultCategoryDataset();
dataset.addValue(15, "1", "451");
dataset.addValue(12, "1", "851");
dataset.addValue(10, "2", "362");
dataset.addValue(5, "2", "142");
return dataset;
}
You will get a chart like this:

Silverlight : How to bind a result of loadoperation to LineSeries chart which contains few null values

I have bound a my chart to a result of load operation. The result returned by the load operation returns complex type with values for some of the object's properties is null.
So I am getting an error in my silver light application.
The code of my XAML is as follows:
<Grid x:Name="LayoutRoot">
<toolkit:Chart Name="historicalTotalChart" Title="Chart Title">
<toolkit:LineSeries >
</toolkit:LineSeries>
</toolkit:Chart>
</Grid>
Code of in my CS file is as follows:
LoadOperation<GetHistoricalTotalReport_Result> hisTotalsLoadOp =
context.Load(context.GetHistoricalToalReportQuery(tableName, sD, startDate, endDate));
LineSeries line = new LineSeries();
line.ItemsSource = hisTotalsLoadOp.Entities;
//line.DependentValuePath ="rep_date";
//line.IndependentValuePath = "expr1";
line.DependentValueBinding = new Binding("[rep_date]");
line.IndependentValueBinding = new Binding("[expr1]");
line.Title = "Historical Totals";
historicalTotalChart.Series.Add(line);
Can any one say how can I over come this error?
rep_date, expr1 are the properties with in my complex type GetHistoricalTotalReport_Result. I am I binding to the properties correctly?
Any help much appreciated.
Thanks
There are 3 possible issues in your application:
Your bindings shouldn't contain square brackets, they are for arrays and dictionaries. Also I would rather use the properties Dependent/IndependentValuePath, you shouldn't comment them, they are completely correct.
The DependentValuePath property must be of a numerical data type, because it is situated on the Y-axis. In your example the rep_date property could be of the double type.
The IndependentValuePath is situated on the X-axis and could be of any type but the values can't contain nulls. Really, I have no idea where a null value can be displayed on the X-axis, it doesn't make sense.
Here is the example of the correct code which works fine:
LineSeries line = new LineSeries();
line.ItemsSource = new[]
{
new ItemViewModel{expr1 = "Item1", rep_date = 25},
new ItemViewModel{expr1 = "Item2", rep_date = null},
new ItemViewModel{expr1 = "Item3", rep_date = 31},
new ItemViewModel{expr1 = "Item4", rep_date = null},
};
line.DependentValuePath = "rep_date";
line.IndependentValuePath = "expr1";
line.Title = "Historical Totals";
historicalTotalChart.Series.Add(line);
The next code will not work:
line.ItemsSource = new[]
{
new ItemViewModel{expr1 = null, rep_date = 25} //wrong, x-value can't be null
}
But you can filter your entities before displaying them:
line.ItemsSource = hisTotalsLoadOp.Entities.Where(e => e.expr1 != null).ToList();

Resources