---
title : FutuerCulclation
robots : noindex, nofollow
lang : ja-jp
breaks : false
---
# FutuerCulclation
# MapConverter.java
```java=
import java.io.File;
import java.util.Map;
import java.util.HashMap;
import java.util.List;
import java.util.ArrayList;
import org.jhotdraw.geom.*;
import maps.MapException;
import maps.gml.GMLMap;
import maps.gml.GMLObject;
import maps.gml.GMLNode;
import maps.gml.GMLEdge;
import maps.gml.GMLShape;
import maps.gml.GMLRoad;
import maps.gml.GMLBuilding;
import maps.gml.GMLSpace;
import maps.gml.GMLDirectedEdge;
import maps.gml.GMLCoordinates;
import maps.gml.formats.RobocupFormat;
import rescuecore2.misc.Pair;
public class MapConverter {
public static void main(String[] args){
List<GMLMap> maps = new ArrayList<GMLMap>();
List<SeparateGMLRoad> roadTypes = new ArrayList<SeparateGMLRoad>();
List<AnalysisMap> analysis = new ArrayList<AnalysisMap>();
MapConvertOptions option = new MapConvertOptions();
option.parseOption(args);
for(String fileName : option.readFileName){
RobocupFormat format = RobocupFormat.INSTANCE;
Map<GMLCoordinates,GMLNode> nodeCheck = new HashMap<GMLCoordinates,GMLNode>();
Map<Pair<GMLNode,GMLNode>,GMLEdge> edgeCheck = new HashMap<Pair<GMLNode,GMLNode>,GMLEdge>();
List<GMLNode> nodes = new ArrayList<GMLNode>();
List<GMLEdge> edges = new ArrayList<GMLEdge>();
List<GMLRoad> roads = new ArrayList<GMLRoad>();
List<GMLBuilding> buildings = new ArrayList<GMLBuilding>();
List<GMLShape> shapes = new ArrayList<GMLShape>();
List<GMLShape> succesList = new ArrayList<GMLShape>();
List<GMLShape> errorShapes = new ArrayList<GMLShape>();
GMLMap map = null;
SeparateGMLRoad roadType = new SeparateGMLRoad();
AnalysisMap analys = null;
File readFile = new File(fileName);
try{
map = format.read(readFile);
}catch(MapException me){
me.printStackTrace();
}
for(GMLObject o : map.getAllObjects()){
if(o instanceof GMLNode){
GMLNode node = (GMLNode)o;
nodeCheck.put(node.getCoordinates(),node);
nodes.add(node);
}else if(o instanceof GMLEdge){
GMLEdge edge = (GMLEdge)o;
edges.add(edge);
edgeCheck.put(new Pair<GMLNode,GMLNode>(edge.getStart(),edge.getEnd()), edge);
edgeCheck.put(new Pair<GMLNode,GMLNode>(edge.getEnd(),edge.getStart()), edge);
}else if(o instanceof GMLShape){
shapes.add((GMLShape)o);
if(o instanceof GMLBuilding){
buildings.add((GMLBuilding)o);
}else if(o instanceof GMLRoad){
GMLRoad r = (GMLRoad)o;
roads.add(r);
}
}else if(o instanceof GMLSpace){
}else{
System.err.println("Unknown Object");
}
}
if(option.checkOverlap){
checkOverlapNode(nodes,map,edges,nodeCheck);
checkOverlapEdge(edges,map,shapes,edgeCheck);
}
//checkShape(map,edges,shapes);
//checkNeighbour(shapes,errorShapes);
if(option.isAnalysis){
roadType.separateRoads(roads, map);
roadType.separateStreet(map);
analys = new AnalysisMap(roadType,map);
analys.detectionSemigloss();
for(GMLBuilding building : buildings){
for(GMLGloss gloss : analys.getGlossList()){
gloss.setBuilding(building);
}
}
for(GMLGloss gloss: analys.getGlossList()){
gloss.calculation();
}
maps.add(map);
roadTypes.add(roadType);
analysis.add(analys);
}
/*
Map<GMLNode,GMLShape> deleteList = new HashMap<GMLNode,GMLShape>();
deleteList.put(new GMLNode(-1,1.0,1.0),new GMLBuilding(-9999)); //dummy
for(int i = 0; i < option.step && deleteList.size() >= 1; ++i){
deleteList.clear();
errorCheck(nodes,shapes,roads,deleteList,map,option.rate,option.robust,succesList);
}
MapViewer view = new MapViewer(roadType,analys.getGlossList(),map,edges,deleteList,map.getMinX(),map.getMinY(),map.getMaxX(),map.getMaxY());
System.out.println("YABAI:"+deleteList.size()+"node:"+nodes.size()+"building:"+buildings.size()+
"road:"+roads.size()+"cross:"+roadType.getCrossing().size());
try{
File newFile = new File(option.writeFileName);
newFile.createNewFile();
try{
format.write(map,newFile);
}catch(MapException me){
me.printStackTrace();
}
}catch(Exception ie){
ie.printStackTrace();
}
*/
}
System.out.println(maps.size());
for(int i = 0; i < maps.size(); ++i){
System.out.println("GROSS_NUM : " + analysis.get(i).getGlossList().size()); // GROSS NUM
// Viewer ON
CalcStatisticDataTool tool = new CalcStatisticDataTool(option.mapNames.get(i),maps.get(i),analysis.get(i).getGlossList(),roadTypes.get(i));
tool.setVisible(true);
//
// Viewer OFF
// CalcStatisticData calc = new CalcStatisticData(analysis.get(i).getGlossList(), maps.get(i), roadTypes.get(i));
// calc.writeFile(option.mapNames.get(i));
}
System.out.println("OWATA");
}
static public void errorCheck(List<GMLNode> nodes,List<GMLShape> shapes,List<GMLRoad> roads,Map<GMLNode,GMLShape> deleteList,GMLMap map,
double rate, double robust, List<GMLShape> succesList){
for(GMLShape r : shapes){
Polygon2D.Double edgeShape = new Polygon2D.Double();
List<GMLNode> nList = new ArrayList<GMLNode>();
boolean succes = true;
if(!succesList.contains(r)){
for(GMLDirectedEdge de : r.getEdges()){
GMLNode tempNode = de.getStartNode();
nList.add(tempNode);
double x;
double y;
if(r.getCentreX() > tempNode.getX()) x = tempNode.getX()+robust;
else x = tempNode.getX() - robust;
if(r.getCentreY() > tempNode.getY()) y = tempNode.getY()+robust;
else y = tempNode.getY() - robust;
edgeShape.addPoint(x,y);
}
for(GMLNode errorNode : nodes){
if(edgeShape.contains(errorNode.getX(),errorNode.getY())){
if(!nList.contains(errorNode)){
System.out.println("ErrorNodeID:"+errorNode.getID()+" x:"+errorNode.getX()+" y:"+errorNode.getY());
if(!deleteList.containsKey(errorNode)){
for(GMLShape shape : shapes){
for(GMLDirectedEdge edge: shape.getEdges()){
if(errorNode.getID() == edge.getStartNode().getID()){
succes = false;
deleteList.put(errorNode,shape);
GMLNode checked = map.getNode(errorNode.getID());
double cx = shape.getCentreX();
double cy = shape.getCentreY();
if(cx == Double.NEGATIVE_INFINITY || cx == Double.POSITIVE_INFINITY
|| cy == Double.POSITIVE_INFINITY || cy == Double.NEGATIVE_INFINITY
||Double.isNaN(cx) || Double.isNaN(cy)){
cx = edge.getEndNode().getX();
cy = edge.getEndNode().getY();
}
double nx = errorNode.getX()+((cx-errorNode.getX())*rate);
double ny = errorNode.getY()+((cy-errorNode.getY())*rate);
checked.setCoordinates(new GMLCoordinates(nx,ny));
break;
}
}
}
}
}
}
}
System.out.println("RoadID:"+r.getID());
}
if(succes){
succesList.add(r);
}
}
}
public static void checkNeighbour(List<GMLShape> shapes, List<GMLShape> errorShapes){
for(GMLShape shape : shapes){
boolean hasNeighbour = false;
for(GMLDirectedEdge edge : shape.getEdges()){
hasNeighbour = shape.hasNeighbour(edge);
if(hasNeighbour) break;
}
if(!hasNeighbour){
errorShapes.add(shape);
}
}
}
public static void checkShape(GMLMap map, List<GMLEdge> edges, List<GMLShape> shapes){
List<GMLObject> deleteList = new ArrayList<GMLObject>();
for(GMLShape shape : shapes){
List<GMLDirectedEdge> newEdgeList = new ArrayList<GMLDirectedEdge>();
List<GMLDirectedEdge> oldEdgeList = shape.getEdges();
/*
for(GMLDirectedEdge edge : newEdgeList){
hasNeighbour = shape.hasNeighbour(edge);
}
if(!hasNeighbour){
oldEdgeList.clear();
GMLNode end = null;
for(GMLDirectedEdge orgEdge: shape.getEdges()){
GMLDirectedEdge newEdge =null;
if(end != null){
if(end.getID() == orgEdge.getStartNode().getID()){
GMLEdge addEdge = map.createEdge(end, orgEdge.getEndNode());
edges.add(addEdge);
oldEdgeList.add(new GMLDirectedEdge(addEdge,end));
}else{
GMLEdge addEdge = map.createEdge(end, orgEdge.getStartNode());
edges.add(addEdge);
oldEdgeList.add(new GMLDirectedEdge(addEdge,end));
}
end = null;
}
for(GMLEdge edge: edges){
if(orgEdge.getEdge().getID()!=edge.getID() &&
(edge.getStart().getID() == orgEdge.getStartNode().getID()||
edge.getStart().getID() == orgEdge.getEndNode().getID())){
newEdge = new GMLDirectedEdge(edge,edge.getStart());
end = edge.getEnd();
break;
}
}
if(newEdge == null){
oldEdgeList.add(orgEdge);
}else{
deleteList.add(orgEdge.getEdge());
oldEdgeList.add(newEdge);
}
}
}*/
GMLDirectedEdge target = (oldEdgeList.get(0));
newEdgeList.add(target);
GMLNode endNode = target.getEndNode();
List<GMLEdge> checkList = new ArrayList<GMLEdge>();
checkList.add(target.getEdge());
for(int i = 1; i <= oldEdgeList.size()-1; ++i){
for(GMLDirectedEdge edge : oldEdgeList){
if(!checkList.contains(edge.getEdge())){
if(endNode.equals(edge.getStartNode())){
newEdgeList.add(edge);
checkList.add(edge.getEdge());
endNode = edge.getEndNode();
break;
}else if(endNode.equals(edge.getStartNode())){
endNode = edge.getEndNode();
edge.reverse();
newEdgeList.add(edge);
checkList.add(edge.getEdge());
break;
}
}
}
}
shape.setEdges(newEdgeList);
}
for(GMLObject delete : deleteList){
map.remove(delete);
}
}
public static void checkOverlapNode(List<GMLNode> nodes, GMLMap map, List<GMLEdge> edges, Map<GMLCoordinates,GMLNode>nodeCheck){
List<GMLNode> errorNode = new ArrayList<GMLNode>();
for(GMLEdge edge : edges){
GMLNode start = nodeCheck.get(edge.getStart().getCoordinates());
GMLNode end = nodeCheck.get(edge.getEnd().getCoordinates());
if(start != null && (!edge.getStart().equals(start))){
errorNode.add(edge.getStart());
edge.setStart(start);
}
if(end != null && (!edge.getEnd().equals(end))){
errorNode.add(edge.getEnd());
edge.setEnd(end);
}
}
for(GMLNode node : errorNode){
map.remove(node);
nodes.remove(node);
}
}
public static void checkOverlapEdge(List<GMLEdge> edges, GMLMap map, List<GMLShape> shapes, Map<Pair<GMLNode,GMLNode>,GMLEdge>edgeCheck){
List<GMLEdge> errorEdge = new ArrayList<GMLEdge>();
for(GMLShape shape :shapes){
for(GMLDirectedEdge edge : shape.getEdges()){
GMLEdge edgeTemp = edgeCheck.get(new Pair<GMLNode,GMLNode>(edge.getStartNode(),edge.getEndNode()));
if(edgeTemp != null && !edgeTemp.equals(edge.getEdge())){
shape.replaceEdge(edge, new GMLDirectedEdge(edgeTemp,edgeTemp.getStart()));
errorEdge.add(edge.getEdge());
}
}
}
for(GMLEdge edge : errorEdge){
map.remove(edge);
edges.remove(edge);
}
}
}
```
## SeparateGMLRoad.java
```java=
import java.util.List;
import java.io.PrintWriter;
import java.util.ArrayList;
import java.util.Map;
import java.util.HashMap;
import maps.gml.GMLRoad;
import maps.gml.GMLNode;
import maps.gml.GMLDirectedEdge;
import maps.gml.GMLBuilding;
import maps.gml.GMLMap;
import maps.gml.GMLObject;
import rescuecore2.misc.Pair;
enum GMLRoadType{
MAIN,
END,
ENTRANCE,
BTOB,
UNKNOWN,
CROSSING
}
public class SeparateGMLRoad {
private List<GMLRoad> mainRoad;
private List<GMLRoad> endRoad;
private List<GMLRoad> entrance;
private List<GMLRoad> buildingToBuilding;
private List<GMLRoad> unknown;
private List<GMLRoad> crossing;
private Map<Integer,GMLRoad> idToCrossing;
private Map<Integer,GMLRoadType> idToType;
private List<GMLStreet> streets;
private Map<Integer,List<Pair<Integer,Integer>>> streetCrossingList;//cross1<street,cross2>
public SeparateGMLRoad(){
mainRoad = new ArrayList<GMLRoad>();
endRoad = new ArrayList<GMLRoad>();
entrance = new ArrayList<GMLRoad>();
buildingToBuilding = new ArrayList<GMLRoad>();
unknown = new ArrayList<GMLRoad>();
crossing = new ArrayList<GMLRoad>();
idToCrossing = new HashMap<Integer,GMLRoad>();
idToType = new HashMap<Integer,GMLRoadType>();
streets = new ArrayList<GMLStreet>();
streetCrossingList = new HashMap<Integer,List<Pair<Integer,Integer>>>();
}
public GMLRoadType separateRoad(GMLRoad road, GMLMap map, List<GMLRoad> checkList){
int roadNeighbour = 0;
int buildingNeighbour = 0;
if(entrance.contains(road)){
return GMLRoadType.ENTRANCE;
}else if(checkList.contains(road)){
return GMLRoadType.MAIN;
}
checkList.add(road);
for(GMLDirectedEdge edge: road.getEdges()){
if(road.hasNeighbour(edge)){
GMLObject object = map.getObject(road.getNeighbour(edge));
if(object instanceof GMLBuilding){
buildingNeighbour++;
}else if(object instanceof GMLRoad){
GMLRoadType type = separateRoad((GMLRoad)object,map,checkList);
if(type == GMLRoadType.MAIN || type == GMLRoadType.END || type == GMLRoadType.CROSSING){
roadNeighbour++;
}
}
}
}
//道分類
if(roadNeighbour >= 3){
crossing.add(road);
idToCrossing.put(road.getID(), road);
idToType.put(road.getID(), GMLRoadType.CROSSING);
return GMLRoadType.CROSSING;
}else if(roadNeighbour >= 2){
mainRoad.add(road);
idToType.put(road.getID(), GMLRoadType.MAIN);
return GMLRoadType.MAIN;
}else if(roadNeighbour == 0 && buildingNeighbour >= 2){
buildingToBuilding.add(road);
idToType.put(road.getID(), GMLRoadType.BTOB);
return GMLRoadType.BTOB;
}else if(roadNeighbour >= 1 && buildingNeighbour >= 1){
entrance.add(road);
idToType.put(road.getID(), GMLRoadType.ENTRANCE);
return GMLRoadType.ENTRANCE;
}else if(roadNeighbour >= 1){
endRoad.add(road);
idToType.put(road.getID(), GMLRoadType.END);
return GMLRoadType.END;
}
unknown.add(road);
idToType.put(road.getID(), GMLRoadType.UNKNOWN);
return GMLRoadType.UNKNOWN;
}
public void separateRoads(List<GMLRoad> roads, GMLMap map){
List<GMLRoad> checkList = new ArrayList<GMLRoad>();
for(GMLRoad road : roads){
int buildingCount = 0;
int roadCount = 0;
List<GMLNode> nodes = new ArrayList<GMLNode>();
for(GMLDirectedEdge edge : road.getEdges()){
if(road.hasNeighbour(edge)){
GMLObject o = map.getObject(road.getNeighbour(edge));
if(o instanceof GMLBuilding){
buildingCount++;
}else if(o instanceof GMLRoad){
roadCount++;
if(!nodes.contains(edge.getStartNode()))
nodes.add(edge.getStartNode());
if(!nodes.contains(edge.getEndNode()))
nodes.add(edge.getEndNode());
}
}
}
if(buildingCount >= 1){
if((roadCount == 2 && nodes.size() <= 3) || roadCount <= 1){
entrance.add(road);
idToType.put(road.getID(), GMLRoadType.ENTRANCE);
}
}
}
for(GMLRoad road : roads){
separateRoad(road,map,checkList);
}
}
public void separateStreet(GMLMap map){
if(mainRoad.isEmpty()){
System.err.println("need separate road!");
return;
}
List<GMLRoad> checkList = new ArrayList<GMLRoad>();
for(GMLRoad road : endRoad){
GMLRoad next = road;
List<GMLRoad> street = new ArrayList<GMLRoad>();
do{
checkList.add(next);
street.add(next);
for(GMLDirectedEdge edge : next.getEdges()){
if(next.hasNeighbour(edge)){
GMLObject o = map.getObject(next.getNeighbour(edge));
if(o instanceof GMLRoad){
GMLRoad temp = (GMLRoad)o;
if(!checkList.contains(temp) && idToType.get(temp.getID())!=GMLRoadType.ENTRANCE){
next = temp;
}
}
}
}
}while(idToType.get(next.getID()) != GMLRoadType.CROSSING);
streets.add(new GMLStreet(street,road.getID(),next.getID(),streets.size()));
}
List<GMLRoad> startRoad = new ArrayList<GMLRoad>();
for(GMLRoad road : crossing){
for(GMLDirectedEdge edge : road.getEdges()){
if(road.hasNeighbour(edge)){
GMLRoad temp = map.getRoad(road.getNeighbour(edge));
if(temp != null && !checkList.contains(temp) && idToType.get(temp.getID())!=GMLRoadType.ENTRANCE && idToType.get(temp.getID())!=GMLRoadType.CROSSING){
if(!startRoad.contains(temp))
startRoad.add(temp);
}else if(temp != null && idToType.get(temp.getID())==GMLRoadType.CROSSING && !checkList.contains(temp)){
List<Pair<Integer,Integer>> streetCross = streetCrossingList.get(road.getID());
if(streetCross == null) streetCross = new ArrayList<Pair<Integer,Integer>>();
streetCross.add(new Pair<Integer,Integer>(-1,temp.getID()));
streetCrossingList.put(road.getID(), streetCross);
}
}
}
}
for(GMLRoad road : startRoad){
if(!checkList.contains(road)){
GMLRoad cross1 = null;
GMLRoad cross2 = null;
int streetID = streets.size();
GMLRoad next = null;
List<GMLRoad> street = new ArrayList<GMLRoad>();
checkList.add(road);
street.add(road);
for(GMLDirectedEdge edge: road.getEdges()){
if(road.hasNeighbour(edge)){
GMLObject o = map.getObject(road.getNeighbour(edge));
if(o instanceof GMLRoad){
if(idToType.get(o.getID()) == GMLRoadType.CROSSING){
if(cross1 != null) cross2 = (GMLRoad)o;
else cross1 = (GMLRoad)o;
}else{
next = (GMLRoad)o;
}
}
}
}
if(next != null){
boolean flag = true;
while(idToType.get(next.getID()) != GMLRoadType.CROSSING && flag){
flag = false;
checkList.add(next);
street.add(next);
for(GMLDirectedEdge edge : next.getEdges()){
if(next.hasNeighbour(edge)){
GMLObject o = map.getObject(next.getNeighbour(edge));
if(o instanceof GMLRoad){
GMLRoad temp = (GMLRoad)o;
if(!checkList.contains(temp) && idToType.get(temp.getID())!=GMLRoadType.ENTRANCE){
next = temp;
flag = true;
}
}
}
}
}
}
if(next != null || cross2 != null){
if(cross2 == null)cross2 = next;
streets.add(new GMLStreet(street,cross1.getID(),cross2.getID(),streets.size()));
List<Pair<Integer,Integer>> streetCross = streetCrossingList.get(cross1.getID());
if(streetCross == null) streetCross = new ArrayList<Pair<Integer,Integer>>();
if(idToType.get(cross2.getID()) == GMLRoadType.CROSSING) streetCross.add(new Pair<Integer,Integer>(streetID,cross2.getID()));
streetCrossingList.put(cross1.getID(), streetCross);
streetCross = streetCrossingList.get(cross2.getID());
if(streetCross == null) streetCross = new ArrayList<Pair<Integer,Integer>>();
if(idToType.get(cross2.getID()) == GMLRoadType.CROSSING) streetCross.add(new Pair<Integer,Integer>(streetID,cross1.getID()));
streetCrossingList.put(cross2.getID(), streetCross);
}
}
}
}
public GMLRoadType getRoadType(GMLRoad road){
return idToType.get(road.getID());
}
public GMLRoadType getRoadType(int bid){
return idToType.get(bid);
}
public List<GMLRoad> getMainRoads(){
return mainRoad;
}
public List<GMLRoad> getEntrance(){
return entrance;
}
public List<GMLRoad> getBtoB(){
return buildingToBuilding;
}
public List<GMLRoad> getEndRoads(){
return endRoad;
}
public List<GMLRoad> getUnknown(){
return unknown;
}
public List<GMLRoad> getCrossing(){
return crossing;
}
public List<GMLStreet> getStreets(){
return streets;
}
public Map<Integer,List<Pair<Integer,Integer>>> getCrossingGraph(){
return streetCrossingList;
}
public Map<Integer,GMLRoad> getIdToCrossing(){
return idToCrossing;
}
public void writeFile(PrintWriter pw){
pw.println("SeparateDataStart");
pw.println("roadType");
for(Integer id : idToType.keySet()){
pw.print(id+":");
switch(idToType.get(id)){
case MAIN:
pw.println("main");
break;
case END:
pw.println("end");
break;
case CROSSING:
pw.println("cross");
break;
case ENTRANCE:
pw.println("entrance");
break;
}
}
pw.println("street");
for(GMLStreet s : streets){
pw.println(s.getID()+":"+s.getStartID()+":"+s.getEndID());
}
}
}
```
## AnalysisMap.java
```java=
import java.util.Map;
import java.util.HashMap;
import java.util.List;
import java.util.ArrayList;
import java.util.Collections;
import rescuecore2.misc.Pair;
import maps.gml.GMLRoad;
import maps.gml.GMLMap;
import org.jhotdraw.geom.*;
public class AnalysisMap{
private int MAX_DISTANCE = 12;
private SeparateGMLRoad separatedRoads;
private Map<Integer,List<Pair<Integer,Integer>>> crossGraph;
private List<List<Integer>> result;
private List<List<GMLRoad>> resultRoads;
private Map<Integer,Integer> glossCrossCount;
private List<List<Integer>> twoCrossGloss;
private List<List<GMLRoad>> twoCrossGlossRoads;
private List<Integer> checkTwoCrossGloss;
private List<Polygon2D.Double> poList;
private List<Polygon2D.Double> twoCrossPoList;
private List<GMLGloss> glossList;
private GMLMap map;
public AnalysisMap(SeparateGMLRoad sRoads, GMLMap map){
this.separatedRoads = sRoads;
crossGraph = separatedRoads.getCrossingGraph();
result = new ArrayList<List<Integer>>();
resultRoads = new ArrayList<List<GMLRoad>>();
twoCrossGloss = new ArrayList<List<Integer>>();
twoCrossGlossRoads = new ArrayList<List<GMLRoad>>();
checkTwoCrossGloss = new ArrayList<Integer>();
glossCrossCount = new HashMap<Integer,Integer>();
for(GMLRoad road : separatedRoads.getCrossing()){
glossCrossCount.put(road.getID(), 0);
}
poList = new ArrayList<Polygon2D.Double>();
twoCrossPoList = new ArrayList<Polygon2D.Double>();
glossList = new ArrayList<GMLGloss>();
this.map = map;
}
private void searchSemigloss(GMLRoad cross){
if(crossGraph.get(cross.getID()) != null){
List<ExtendedCrossing> glossList = new ArrayList<ExtendedCrossing>();
List<Integer> checkedCross = new ArrayList<Integer>();
List<Integer> neighbours = new ArrayList<Integer>();
int numStreet = crossGraph.get(cross.getID()).size();
int numNeedGloss = numStreet;
if(numStreet <= 3) numNeedGloss--;
for(int i = 0; i < crossGraph.get(cross.getID()).size(); ++i){
Pair<Integer, Integer> street = crossGraph.get(cross.getID()).get(i);
if(separatedRoads.getIdToCrossing().get(street.second()) == null) System.out.println(street.second());
else glossList.add(new ExtendedCrossing(separatedRoads.getIdToCrossing().get(street.second()),cross,street.first()));
neighbours.add(street.second());
for(int j = i+1; j < crossGraph.get(cross.getID()).size(); ++j){
Pair<Integer, Integer> street2 = crossGraph.get(cross.getID()).get(j);
if(street.second().equals(street2.second()) && !checkTwoCrossGloss.contains(street.second())){
checkTwoCrossGloss.add(cross.getID());
checkTwoCrossGloss.add(street2.second());
List<Integer> c = new ArrayList<Integer>();
c.add(street.second());
c.add(cross.getID());
twoCrossGloss.add(c);
GMLStreet gs = null;
if(street.first() != -1) gs = separatedRoads.getStreets().get(street.first());
GMLStreet gs2 = null;
if(street2.first() != -1) gs2 = separatedRoads.getStreets().get(street2.first());
List<GMLRoad> roadList = new ArrayList<GMLRoad>();
Polygon2D.Double p2 = new Polygon2D.Double();
if(gs != null && gs2 != null){
for(GMLRoad road : gs.getRoads()){
roadList.add(road);
p2.addPoint(road.getCentreX(), road.getCentreY());
}
roadList.add(separatedRoads.getIdToCrossing().get(gs.getEndID()));
if(gs.getEndID() == gs2.getStartID()){
for(GMLRoad road : gs2.getRoads()){
roadList.add(road);
p2.addPoint(road.getCentreX(), road.getCentreY());
}
GMLRoad road = separatedRoads.getIdToCrossing().get(gs2.getEndID());
roadList.add(road);
p2.addPoint(road.getCentreX(), road.getCentreY());
}else{
for(int k = gs2.getRoads().size()-1; k >= 0; --k){
GMLRoad road = gs2.getRoads().get(k);
roadList.add(road);
p2.addPoint(road.getCentreX(), road.getCentreY());
}
GMLRoad road = separatedRoads.getIdToCrossing().get(gs2.getStartID());
roadList.add(road);
p2.addPoint(road.getCentreX(), road.getCentreY());
}
}else if(gs == null && gs2 != null){
GMLRoad start = separatedRoads.getIdToCrossing().get(gs2.getStartID());
GMLRoad end = separatedRoads.getIdToCrossing().get(gs2.getEndID());
roadList.add(start);
p2.addPoint(start.getCentreX(), start.getCentreY());
for(GMLRoad r : gs2.getRoads()){
roadList.add(r);
p2.addPoint(r.getCentreX(), r.getCentreY());
}
roadList.add(end);
p2.addPoint(end.getCentreX(), end.getCentreY());
}else if(gs2 == null && gs != null){
GMLRoad start = separatedRoads.getIdToCrossing().get(gs.getStartID());
GMLRoad end = separatedRoads.getIdToCrossing().get(gs.getEndID());
roadList.add(start);
p2.addPoint(start.getCentreX(), start.getCentreY());
for(GMLRoad r : gs.getRoads()){
roadList.add(r);
p2.addPoint(r.getCentreX(), r.getCentreY());
}
roadList.add(end);
p2.addPoint(end.getCentreX(), end.getCentreY());
}else{
GMLRoad r = separatedRoads.getIdToCrossing().get(street.second());
roadList.add(cross);
roadList.add(r);
p2.addPoint(cross.getCentreX(), cross.getCentreY());
p2.addPoint(r.getCentreX(), r.getCentreY());
}
twoCrossGlossRoads.add(roadList);
twoCrossPoList.add(p2);
}
}
}
Collections.sort(glossList,new CrossComparator());
ExtendedCrossing next;
int numCompleteGloss = 0;
if(glossList.size() > 0) {
next=glossList.get(0);
for(;numCompleteGloss < numNeedGloss;){
glossList.remove(0);
if(cross.getID() == next.getID()){
List<Integer> r = next.getCrossHistory();
r.remove(0);
checkedCross.addAll(r);
if(!checkCompleted(r)){
result.add(r);
numCompleteGloss++;
List<GMLRoad> roads = new ArrayList<GMLRoad>();
Polygon2D.Double p = new Polygon2D.Double();
for(int i = 0; i < next.getStreetHistory().size(); ++i){
GMLRoad cr = separatedRoads.getIdToCrossing().get(r.get(i));
if(next.getStreetHistory().get(i) != -1){
GMLStreet start = separatedRoads.getStreets().get(next.getStreetHistory().get(i));
if(cr.getID() != start.getStartID()){
for(int j = 0; j < start.getRoads().size(); ++j){
GMLRoad road = start.getRoads().get(j);
roads.add(road);
p.addPoint(road.getCentreX(), road.getCentreY());
}
}else{
for(int j = start.getRoads().size()-1; j >= 0; --j){
GMLRoad road = start.getRoads().get(j);
roads.add(road);
p.addPoint(road.getCentreX(), road.getCentreY());
}
}
}
roads.add(cr);
p.addPoint(cr.getCentreX(), cr.getCentreY());
}
resultRoads.add(roads);
poList.add(p);
for(Integer id : r){
glossCrossCount.put(id,glossCrossCount.get(id)+1);
}
}
}else if((!checkedCross.contains(next.getID()) || neighbours.contains(next.getID()))&&next.getCount()<=MAX_DISTANCE){
for(Pair<Integer,Integer> street : crossGraph.get(next.getID())){
if((!next.getCrossHistory().contains(street.second())) || (street.second()==cross.getID()&&next.getCount()>=3)){
List<Integer> streets = new ArrayList<Integer>();
List<Integer> crosses = new ArrayList<Integer>();
crosses.addAll(next.getCrossHistory());
streets.addAll(next.getStreetHistory());
crosses.add(street.second());
streets.add(street.first());
if(separatedRoads.getIdToCrossing().get(street.second()) != null)
glossList.add(new ExtendedCrossing(separatedRoads.getIdToCrossing().get(street.second()),cross,crosses,streets));
}
}
}
if(glossList.isEmpty()){
break;
}else{
Collections.sort(glossList,new CrossComparator());
next=glossList.get(0);
}
}
}
}
}
public void detectionSemigloss(){
for(GMLRoad cross : separatedRoads.getCrossing()){
searchSemigloss(cross);
}
result.addAll(twoCrossGloss);
resultRoads.addAll(twoCrossGlossRoads);
poList.addAll(twoCrossPoList);
checkResult();
MAX_DISTANCE += 4;
for(Integer id : glossCrossCount.keySet()){
if(glossCrossCount.get(id) == 0){
searchSemigloss(separatedRoads.getIdToCrossing().get(id));
}
}
for(int i = 0; i < result.size(); ++i){
glossList.add(new GMLGloss(resultRoads.get(i)));
}
}
public boolean checkCompleted(List<Integer> check){
boolean isChecked = false;
for(List<Integer> r : result){
int count = 0;
for(Integer id2 : r){
if(check.contains(id2)) count++;
}
if(count >= r.size()){
isChecked = true;
break;
}
}
return isChecked;
}
public void checkResult(){
List<List<Integer>> deleteCross = new ArrayList<List<Integer>>();
List<List<GMLRoad>> deleteRoads = new ArrayList<List<GMLRoad>>();
List<Polygon2D> deletePoly = new ArrayList<Polygon2D>();
for(int i = 0; i < resultRoads.size()-1; ++i){
List<GMLRoad> list1 = resultRoads.get(i);
for(int j = i+1; j < resultRoads.size(); ++j){
List<GMLRoad> list2 = resultRoads.get(j);
List<GMLRoad> small = list2;
List<GMLRoad> big = list1;
int bigNum = i;
int smallNum = j;
if(list1.size() < list2.size()){
big =list2;
small = list1;
bigNum = j;
smallNum = i;
}
if(list1.size() != list2.size()){
int pCount = 0;
int gCount = 0;
for(GMLRoad road : small){
if(big.contains(road)){
pCount++;
}else if(poList.get(bigNum).contains(road.getCentreX(), road.getCentreY())){
gCount++;
}
}
if(pCount+gCount == small.size()){
if(result.get(smallNum).size() == 2){
//------------------------------------------------------
List<GMLRoad> bigGloss = resultRoads.get(bigNum);
List<GMLRoad> smallGloss = resultRoads.get(smallNum);
List<GMLRoad> deleteTwoRoads = new ArrayList<GMLRoad>();
List<GMLRoad> addTwoRoads = new ArrayList<GMLRoad>();
boolean check = false;
int index = -1;
GMLRoad startR = null;
GMLRoad endR = null;
addTwoRoads.addAll(smallGloss);
for(int k = 0; k < bigGloss.size(); ++k){
GMLRoad r = bigGloss.get(k);
if(GMLRoadType.CROSSING != separatedRoads.getRoadType(r)){
if(smallGloss.contains(r)) deleteTwoRoads.add(r);
}
if(r.equals(separatedRoads.getIdToCrossing().get(result.get(smallNum).get(0)))){
if(!check){
check = true;
index = k;
startR = separatedRoads.getIdToCrossing().get(result.get(smallNum).get(0));
endR = separatedRoads.getIdToCrossing().get(result.get(smallNum).get(1));
}
}else if(r.equals(separatedRoads.getIdToCrossing().get(result.get(smallNum).get(1)))){
if(!check){
check = true;
index = k;
startR = separatedRoads.getIdToCrossing().get(result.get(smallNum).get(1));
endR = separatedRoads.getIdToCrossing().get(result.get(smallNum).get(0));
}
}
}
bigGloss.removeAll(deleteTwoRoads);
bigGloss.remove(separatedRoads.getIdToCrossing().get(result.get(smallNum).get(0)));
bigGloss.remove(separatedRoads.getIdToCrossing().get(result.get(smallNum).get(1)));
addTwoRoads.removeAll(deleteTwoRoads);
if(index > bigGloss.size()){
index = bigGloss.size();
}
int startIndex = addTwoRoads.indexOf(startR);
int endIndex = addTwoRoads.indexOf(endR);
List<GMLRoad> addTwoRoads2 = new ArrayList<GMLRoad>();
if(endIndex < startIndex){
for(int l = addTwoRoads.size()-1; l >= 0 ;--l){
addTwoRoads2.add(addTwoRoads.get(l));
}
}else{
addTwoRoads2 = addTwoRoads;
}
if(index < 0) bigGloss.addAll(0, addTwoRoads2);
else bigGloss.addAll(index, addTwoRoads2);
//-------------------------------------
}else{
deleteCross.add(result.get(bigNum));
deleteRoads.add(resultRoads.get(bigNum));
deletePoly.add(poList.get(bigNum));
}
}
}
}
}
result.removeAll(deleteCross);
resultRoads.removeAll(deleteRoads);
poList.removeAll(deletePoly);
}
public Map<Integer,Integer> getGlossCrossCount(){
return glossCrossCount;
}
public List<List<Integer>> getResult(){
return result;
}
public List<GMLGloss> getGlossList(){
return glossList;
}
}
```
## CalcStatisticData.java
```java=
import java.util.List;
import java.io.File;
import java.io.BufferedWriter;
import java.io.PrintWriter;
import java.io.FileWriter;
import maps.gml.GMLRoad;
import maps.gml.GMLBuilding;
import maps.gml.GMLMap;
import maps.gml.GMLDirectedEdge;
import maps.gml.GMLCoordinates;
import java.util.Map;
import java.util.HashMap;
import java.math.BigDecimal;
public class CalcStatisticData {
private double c1;
private double c9;
private double c13;
private double c13num;
private double buildingCoverage;//
private double buildingLength;//
private double buildingDependent;//
private double maxAdjacentDistance;//
private double distributionRatio;//
private double contactRoadDistance;//
private BigDecimal clearance;//
private BigDecimal roadLength;
private double roadDensity;//
private BigDecimal buildingNumberDensity;//
Map<Integer,Double> roads;
public CalcStatisticData(List<GMLGloss> glossList, GMLMap map, SeparateGMLRoad separate){
buildingCoverage = 0;
c1 = 0;
buildingLength = 0;
buildingDependent = 0;
maxAdjacentDistance = 0;
c9 = 0;
distributionRatio = 0;
c13 = 0;
c13num = 0;
contactRoadDistance = 0;
clearance = new BigDecimal(0);
roadLength = new BigDecimal(0);
roadDensity = 0;
for(GMLGloss gloss : glossList){
//buildings-----------------------------------------------
int bNum = gloss.getBuildingsInArea().size();
if(bNum > 0){
double bD = 0;
double bC = 0;
double mL = 0;
double dR = 0;
double MinL = 0;
for(GMLBuilding b : gloss.getBuildingsInArea()){
double maxDependArea = Double.MIN_VALUE;
double maxLength = Double.MIN_VALUE;
double minLength = Double.MAX_VALUE;
bC+=gloss.getBuildingsArea().get(b.getID());
for(Integer id : gloss.getNeighbourBuildings().get(gloss.getBuildingIdInGloss(b.getID()))){
double length = gloss.getBuildingToBuildings().get(b.getID()).get(id);
double area = gloss.getBuildingsArea().get(id);
if(maxDependArea < area) maxDependArea = area;
if(maxLength < length) maxLength = length;
if(minLength > length) minLength = length;
}
if(maxDependArea != Double.MIN_VALUE) bD += maxDependArea/gloss.getBuildingsArea().get(b.getID());
if(maxLength != Double.MIN_VALUE){
mL += maxLength;
MinL += minLength;
dR += (maxLength - minLength) / maxLength;
}
}
double tmpGloss = Math.sqrt(gloss.getArea());
c1 += bC/Math.pow(tmpGloss + 1.5, 2);
buildingCoverage += bC/gloss.getArea();
buildingDependent += bD/bNum;
maxAdjacentDistance += mL/bNum;
c9 += MinL/bNum;
distributionRatio += dR/bNum;
//buildingsEnd------------------------------------------------------
}
int rLCount = 0;
double crd = 0;
for(Integer id : gloss.getSemiGlossToBuildings().keySet()){
for(Double length : gloss.getSemiGlossToBuildings().get(id)){
crd += length;
rLCount++;
}
}
if(rLCount > 0) {
contactRoadDistance += crd/rLCount;
}
if(gloss.getFollowBuildings().size() > 0) {
}
if(gloss.getFollowBuildings().size() > 0) {
c13num += gloss.getFollowBuildings().size();
for(List l : gloss.getFollowBuildings()) {
if(l.size() > 0) {
c13 += l.size();
}
}
}
if(gloss.getClearance().size() > 0){
BigDecimal cl = new BigDecimal(0);
for(Double c : gloss.getClearance()){
if(c > 0){
cl = cl.add(new BigDecimal(c));
}
}
cl = cl.divide(new BigDecimal(gloss.getClearance().size()),BigDecimal.ROUND_HALF_UP);
clearance = clearance.add(cl);
}
}
//end Gloss --------------------------------------------
buildingCoverage = buildingCoverage/glossList.size();
c1 = c1/glossList.size();
buildingDependent = buildingDependent/glossList.size();
maxAdjacentDistance = maxAdjacentDistance/glossList.size();
c9 = c9/glossList.size();
distributionRatio = distributionRatio/glossList.size();
contactRoadDistance = contactRoadDistance/glossList.size();
clearance = clearance.divide(new BigDecimal(glossList.size()),BigDecimal.ROUND_HALF_UP);
c13 = c13/c13num;
double mapArea = (map.getMaxX()-map.getMinX()) * (map.getMaxY()-map.getMinY());
buildingNumberDensity = new BigDecimal(map.getBuildings().size()/mapArea);
for(GMLBuilding b : map.getBuildings()){
double bL = 0;
for(GMLDirectedEdge edge : b.getEdges()){
double x1 = edge.getStartNode().getX();
double y1 = edge.getStartNode().getY();
double x2 = edge.getEndNode().getX();
double y2 = edge.getEndNode().getY();
bL += Math.sqrt(((x1-x2)*(x1-x2))+((y1-y2)*(y1-y2)));
}
buildingLength += bL;
}
buildingLength = buildingLength/map.getBuildings().size();
roads = new HashMap<Integer,Double>();
for(GMLRoad r : map.getRoads()){
double roadArea = 0;
double cx = r.getCentreX();
double cy = r.getCentreY();
List<GMLCoordinates> point = r.getCoordinates();
for(int i = point.size(),u=0;i-->0;u=i){
roadArea += (point.get(i).getX()-point.get(u).getX())*(point.get(i).getY()+point.get(u).getY());
}
roadDensity += Math.abs(0.5*roadArea);
for(GMLDirectedEdge edge : r.getEdges()){
double length = 0;
if(r.hasNeighbour(edge)){
if(map.getObject(r.getNeighbour(edge)) instanceof GMLRoad){
if(separate.getRoadType(r.getNeighbour(edge)) != GMLRoadType.ENTRANCE){
double x = edge.getStartNode().getX() - (edge.getStartNode().getX()-edge.getEndNode().getX());
double y = edge.getStartNode().getY() - (edge.getStartNode().getY()-edge.getEndNode().getY());
length = Math.sqrt((cx-x)*(cx-x)+(cy-y)*(cy-y));
if(separate.getRoadType(r) == GMLRoadType.END) length *= 2;
if(separate.getRoadType(r) != GMLRoadType.ENTRANCE){
if(Double.isInfinite(length) || Double.isNaN(length)){
System.out.println(r.getID());
}else{
System.out.println(length);
roadLength = roadLength.add(new BigDecimal(length));
}
if(roads.containsKey(r.getID()))
roads.put(r.getID(), roads.get(r.getID())+length);
else
roads.put(r.getID(), length);
}
}
}
}
}
}
roadDensity = roadDensity/mapArea;
}
public Map<Integer,Double> getRoads(){
return roads;
}
public void writeFile(String name){
try{
File file = new File(name+".csv");
PrintWriter pw = new PrintWriter(new BufferedWriter(new FileWriter(file)));
pw.println("c1,c2,c5,c7,c8,c9,c10,c11,c12,c13,c14,c15,c16");
pw.print(c1+","+buildingCoverage+","+buildingLength+","+buildingDependent+","+maxAdjacentDistance+","+c9+","+distributionRatio+","+contactRoadDistance+","+clearance+","+c13+","+roadLength+","+roadDensity+","+buildingNumberDensity);
pw.flush();
pw.close();
System.out.println(file.getName()+ "Finish!");
}catch(Exception e){
e.printStackTrace();
}
}
}
```
## GMLGloss.java
```java=
import maps.gml.GMLBuilding;
import maps.gml.GMLRoad;
import maps.gml.GMLDirectedEdge;
import maps.gml.GMLCoordinates;
import rescuecore2.misc.gui.ScreenTransform;
import org.jhotdraw.geom.*;
import java.util.List;
import java.util.ArrayList;
import java.util.Map;
import java.util.HashMap;
import java.awt.Polygon;
import java.awt.geom.Line2D;
import java.awt.geom.Point2D;
import rescuecore2.misc.Pair;
public class GMLGloss {
private List<GMLRoad> roads;
private double semiGlossArea;
private Polygon2D.Double gloss;
private List<GMLBuilding> buildingsInArea;
private Map<Integer,Double> buildingsArea;
private List<GMLDirectedEdge> semiGloss;
private List<Polygon2D> semiGlossShape;
private List<GMLCoordinates> semiGlossPoints;
private List<List<GMLBuilding>> followBuildings;
private List<Double> clearance;
private List<Double> length;
private List<List<Integer>> neighbourBuildings;
private Map<Integer,List<Double>> semiGlossToBuildings;
private Map<Integer,Map<Integer,Double>> buildingToBuildings;
public GMLGloss(List<GMLRoad> roads){
this.roads = roads;
gloss = new Polygon2D.Double();
semiGlossArea = 0;
semiGloss = new ArrayList<GMLDirectedEdge>();
semiGlossShape = new ArrayList<Polygon2D>();
semiGlossPoints = new ArrayList<GMLCoordinates>();
buildingsArea = new HashMap<Integer,Double>();
followBuildings = new ArrayList<List<GMLBuilding>>();
clearance = new ArrayList<Double>();
length = new ArrayList<Double>();
neighbourBuildings = new ArrayList<List<Integer>>();
semiGlossToBuildings = new HashMap<Integer,List<Double>>();
buildingToBuildings = new HashMap<Integer,Map<Integer,Double>>();
int index = 1;
for(GMLRoad road : roads){
if(index >= roads.size()) index = 0;
gloss.addPoint(road.getCentreX(), road.getCentreY());
for(GMLDirectedEdge edge : road.getEdges()){
if(road.hasNeighbour(edge)){
if(road.getNeighbour(edge).intValue() == roads.get(index).getID()){
gloss.addPoint((edge.getStartCoordinates().getX()+edge.getEndNode().getX())/2, (edge.getStartCoordinates().getY()+edge.getEndNode().getY())/2);
}
}
}
index++;
}
for(GMLRoad road : roads){
for(GMLDirectedEdge edge : road.getEdges()){
GMLCoordinates p1 = edge.getStartCoordinates();
GMLCoordinates p2 = edge.getEndCoordinates();
if(gloss.contains(p1.getX(), p1.getY()) && gloss.contains(p2.getX(), p2.getY())){
if(!semiGloss.contains(edge)){
semiGloss.add(edge);
semiGlossShape.add(getPolygon2DFromEdge(edge,5.0));
}
if(!semiGlossPoints.contains(p1)){
semiGlossPoints.add(p1);
}
if(!semiGlossPoints.contains(p2)){
semiGlossPoints.add(p2);
}
}
}
}
for(int i=semiGlossPoints.size(),u=0;i-->0;u=i){
semiGlossArea += (semiGlossPoints.get(i).getX()-semiGlossPoints.get(u).getX())*(semiGlossPoints.get(i).getY()+semiGlossPoints.get(u).getY());
}
semiGlossArea = Math.abs(0.5*semiGlossArea);
buildingsInArea = new ArrayList<GMLBuilding>();
}
public void calculation(){
calcBuildingArea();
followBuildings();
calcClearance();
neighbourBuildings();
for(GMLBuilding b : buildingsInArea){
if(!semiGlossToBuildings.containsKey(b.getID())){
semiGlossToBuildings.put(b.getID(), calcContactRoadDistance(b));
}
}
}
private void calcBuildingArea(){
if(buildingsInArea.size() <= 0) return;
for(GMLBuilding building : buildingsInArea){
double buildingArea = 0;
List<GMLCoordinates> point = building.getCoordinates();
for(int i = point.size(),u=0;i-->0;u=i){
buildingArea += (point.get(i).getX()-point.get(u).getX())*(point.get(i).getY()+point.get(u).getY());
}
buildingsArea.put(building.getID(),Math.abs(0.5*buildingArea));
}
}
private void followBuildings(){
int count = 0;
for(Polygon2D fArea : semiGlossShape){
List<GMLBuilding> fB = new ArrayList<GMLBuilding>();
Polygon2D.Double fA = (Polygon2D.Double)fArea;
GMLCoordinates start = semiGloss.get(count).getStartCoordinates();
GMLCoordinates end = semiGloss.get(count).getEndCoordinates();
Line2D line1 = new Line2D.Double(start.getX(), start.getY(), end.getX(), end.getY());
for(int i = 0; i < buildingsInArea.size(); ++i){
GMLBuilding building = buildingsInArea.get(i);
List<GMLDirectedEdge> edges = building.getEdges();
double length = Double.MAX_VALUE;
for(int j = 0; j < edges.size(); ++j){
GMLDirectedEdge edge = edges.get(j);
Line2D.Double line2 = new Line2D.Double(edge.getStartNode().getX(), edge.getStartNode().getY(), edge.getEndNode().getX(), edge.getEndNode().getY());
if(contains(fA,line2)){
if(!fB.contains(building)){
fB.add(building);
}
if(fA.contains(line2.getP1())){
double temp = line1.ptLineDist(line2.getP1());
if(length > temp) length = temp;
}
if(fA.contains(line2.getP2())){
double temp = line1.ptLineDist(line2.getP2());
if(length > temp) length = temp;
}
if(length == Double.MAX_VALUE){
Polygon2D fA2 = this.getPolygon2DFromEdge(edge, 100);
if(fA2.contains(line1.getP1())){
double temp = line2.ptLineDist(line1.getP1());
if(length > temp) length = temp;
}
if(fA2.contains(line1.getP2())){
double temp = line2.ptLineDist(line1.getP1());
if(length > temp) length = temp;
}
}
}
}
if(length != Double.MAX_VALUE){
List<Double> lengthList = new ArrayList<Double>();
if(semiGlossToBuildings.containsKey(building.getID())){
lengthList = semiGlossToBuildings.get(building.getID());
}
lengthList.add(length);
semiGlossToBuildings.put(building.getID(), lengthList);
}
}
followBuildings.add(fB);
count++;
}
}
private boolean contains(Polygon2D area, Line2D line){
Polygon2D.Double fA = (Polygon2D.Double)area;
Line2D.Double line1 = (Line2D.Double)line;
if(fA.contains(line1.getP1()) && fA.contains(line1.getP2())) return true;
for(int k = 0; k < fA.npoints; ++k){
int next = k+1;
if(next == fA.npoints) next = 0;
Line2D.Double line2 = new Line2D.Double(fA.xpoints[k], fA.ypoints[k], fA.xpoints[next], fA.ypoints[next]);
if((line1.intersectsLine(line2))){
if(line1.ptLineDist(line2.getP1())!=0 && line1.ptLineDist(line2.getP2())!=0 && line2.ptLineDist(line1.getP1())!=0 && line2.ptLineDist(line1.getP2())!=0){
return true;
}else{
Point2D center = new Point2D.Double(line1.x1+((line1.x2-line1.x1)/2),line1.y1+((line1.y2-line1.y2)/2));
if(fA.contains(center)){
return true;
}
}
}
}
return false;
}
private void calcClearance(){
for(int i = 0; i < semiGloss.size(); ++i){
GMLDirectedEdge edge = semiGloss.get(i);
double length = Math.sqrt((edge.getStartNode().getX()-edge.getEndNode().getX())*(edge.getStartNode().getX()-edge.getEndNode().getX())+(edge.getStartNode().getY()-edge.getEndNode().getY())*(edge.getStartNode().getY()-edge.getEndNode().getY()));
double bL = 0;
for(GMLBuilding building : followBuildings.get(i)){
double[] ra = range(building,edge);
bL += ra[1]-ra[0];
}
double cL = length - bL;
clearance.add(cL/length);
this.length.add(length);
}
}
private double[] range(GMLBuilding building, GMLDirectedEdge road) {
Vector2d x;
Vector2d r = new Vector2d(road.getStartNode().getX(), road.getStartNode().getY(), road.getEndNode().getX(), road.getEndNode().getY());
double min=Double.MAX_VALUE, max = Double.MIN_VALUE, length;
double rlength = r.length();
Vector2d ix;
Vector2d ir = new Vector2d(r);
double dot1, dot2;
ir.inverse();
// road to normal vector
r.normalize();
for (GMLCoordinates v : building.getCoordinates())
{
x = new Vector2d(road.getStartNode().getX(), road.getStartNode().getY(), v.getX(), v.getY());
length = Math.abs(r.projection(x));
ix = new Vector2d(road.getEndNode().getX(), road.getEndNode().getY(), v.getX(), v.getY());
dot1 = r.dot(x);
dot2 = ir.dot(ix);
if(dot1 <= 0) { //if(dot1 < 0) {
length = 0;
}
if (dot2 <= 0) { //if (dot2 < 0) {
length = rlength;
}
if (max < length)
{
max = length;
}
if (min > length)
{
min = length;
}
}
// create result
double[] res = new double[2];
res[0] = min;
res[1] = max;
return res;
}
private void neighbourBuildings(){
double maxRange = gloss.getBounds2D().getWidth()+gloss.getBounds2D().getHeight();
for(GMLBuilding building1 : buildingsInArea){
List<Integer> neighbourBuilding = new ArrayList<Integer>();
Map<Integer,Double> b2bLength = new HashMap<Integer,Double>();
for(GMLDirectedEdge edge1 : building1.getEdges()){
double minValue = Double.MAX_VALUE;
int minID = -1;
Line2D line1 = new Line2D.Double(edge1.getStartNode().getX(), edge1.getStartNode().getY(), edge1.getEndNode().getX(), edge1.getEndNode().getY());
Polygon2D p2 = this.getPolygon2DFromEdge(edge1, maxRange);
for(GMLBuilding building2 : buildingsInArea){
if(!building1.equals(building2)){
for(GMLDirectedEdge edge2 : building2.getEdges()){
if(edge1.getEdge().equals(edge2.getEdge())){
minValue = 0;
minID = building2.getID();
b2bLength.put(minID, minValue);
}else{
Line2D line2 = new Line2D.Double(edge2.getStartNode().getX(), edge2.getStartNode().getY(), edge2.getEndNode().getX(), edge2.getEndNode().getY());
if(contains(p2,line2)){
double l = Double.MAX_VALUE;
if(p2.contains(line2.getP1())){
double temp = line1.ptLineDist(line2.getP1());
if(l > temp && temp != 0) l = temp;
}
if(p2.contains(line2.getP2())){
double temp = line1.ptLineDist(line2.getP2());
if(l > temp && temp != 0) l = temp;
}
if(l == Double.MAX_VALUE){
Polygon2D p22 = getPolygon2DFromEdge(edge2,maxRange);
if(p22.contains(line1.getP1())){
double temp = line2.ptLineDist(line1.getP1());
if(l > temp && temp != 0) l = temp;
}
if(p22.contains(line1.getP2())){
double temp = line2.ptLineDist(line1.getP2());
if(l > temp && temp != 0) l = temp;
}
}
if(minValue >= l && l >= 0){
if(b2bLength.containsKey(building2.getID())){
double ml = b2bLength.get(building2.getID());
if(ml > l){
b2bLength.put(building2.getID(), l);
}
}else{
b2bLength.put(building2.getID(), l);
}
if(minValue != l){
minValue = l;
minID = building2.getID();
}
}
}
}
}
}
}
if(minID != -1){
neighbourBuilding.add(minID);
}
}
neighbourBuildings.add(neighbourBuilding);
buildingToBuildings.put(building1.getID(),b2bLength);
}
}
private List<Double> calcContactRoadDistance(GMLBuilding b){
List<Double> result = new ArrayList<Double>();
double maxRange = gloss.getBounds2D().getWidth()+gloss.getBounds2D().getHeight();
double minLength = Double.MAX_VALUE;
for(int i = 0; i < gloss.npoints; ++i){
int next = i+1;
if(next == gloss.npoints) next = 0;
Line2D line1 = new Line2D.Double(gloss.xpoints[i], gloss.ypoints[i], gloss.xpoints[next], gloss.ypoints[next]);
Polygon2D pA = this.getPolygon2DFromEdge(line1, maxRange);
for(GMLCoordinates p : b.getCoordinates()){
if(pA.contains(p.getX(), p.getY())){
double temp = line1.ptLineDist(p.getX(), p.getY());
if(minLength > temp) minLength = temp;
}
}
}
if(minLength == Double.MAX_VALUE) System.out.println("YABASHI");
for(GMLDirectedEdge edge : semiGloss){
Polygon2D pA = getPolygon2DFromEdge(edge,maxRange);
Line2D line1 = new Line2D.Double(edge.getStartNode().getX(), edge.getStartNode().getY(), edge.getEndNode().getX(), edge.getEndNode().getY());
for(GMLCoordinates p : b.getCoordinates()){
if(pA.contains(p.getX(), p.getY())){
double temp = line1.ptLineDist(p.getX(), p.getY());
if(minLength > temp) result.add(temp);
}
}
}
return result;
}
private double calcl2lLength(Line2D line1, Line2D line2){
double result = Double.MAX_VALUE;
double temp;
double x1 = line1.getX1();
double y1 = line1.getY1();
double x2 = line1.getX2();
double y2 = line1.getY2();
double x3 = line2.getX1();
double y3 = line2.getY1();
double x4 = line2.getX2();
double y4 = line2.getY2();
if(Math.abs(x1-x2) == Math.abs(x3-x4) && Math.abs(y1-y2) == Math.abs(y3-y4)){
return line1.ptLineDist(x3, y3);
}
if((x1>x3&&x1<x4) || (x1>x4&&x1<x3) || (y1>y3&&y1<y4) || (y1>y4&&y1<y3)){
temp = line2.ptLineDist(x1, y1);
if(result > temp && temp > 0) result = temp;
}
if((x2>x3&&x2<x4) || (x2>x4&&x2<x3) || (y2>y3&&y2<y4) || (y2>y4&&y2<y3)){
temp = line2.ptLineDist(x2, y2);
if(result > temp && temp > 0) result = temp;
}
if((x3>x1&&x3<x2) || (x3>x2&&x3<x1) || (y3>y1&&y3<y2) || (y3>y2&&y3<y1)){
temp = line1.ptLineDist(x3,y3);
if(result > temp && temp > 0) result = temp;
}
if((x4>x1&&x4<x2) || (x4>x2&&x4<x1) || (y4>y1&&y4<y2) || (y4>y2&&y4<y1)){
temp = line1.ptLineDist(x4,y4);
if(result > temp && temp > 0) result = temp;
}
if(result == Double.MAX_VALUE) return -1;
else return result;
}
private double calcl2lLength(double x1, double y1, double x2, double y2, double x3, double y3, double x4, double y4){
double result = Double.MAX_VALUE;
double temp;
Line2D.Double line1 = new Line2D.Double(x1, y1, x2, y2);
Line2D.Double line2 = new Line2D.Double(x3, y3, x4, y4);
return calcl2lLength(line1,line2);
}
public Map<Integer,List<Double>> getSemiGlossToBuildings(){
return semiGlossToBuildings;
}
public Map<Integer,Map<Integer,Double>> getBuildingToBuildings(){
return buildingToBuildings;
}
public List<GMLDirectedEdge> getSemiGloss(){
return semiGloss;
}
public List<List<GMLBuilding>> getFollowBuildings(){
return followBuildings;
}
public List<Double> getClearance(){
return clearance;
}
public List<Double> getLength(){
return length;
}
public int getBuildingIdInGloss(int buildingID){
int i = 0;
for(GMLBuilding b : buildingsInArea){
if(b.getID() == buildingID) return i;
i++;
}
return -1;
}
public List<Integer> getRoadIdInGloss(GMLRoad road){
List<Integer> result = new ArrayList<Integer>();
for(GMLDirectedEdge edge : road.getEdges()){
int i = 0;
for(GMLDirectedEdge edge2 : semiGloss){
if(edge.equals(edge2)) result.add(i);
i++;
}
}
return result;
}
public List<Polygon> getSemiGlossShape(ScreenTransform trans){
List<Polygon> result = new ArrayList<Polygon>();
for(Polygon2D p2 : semiGlossShape){
Polygon p = new Polygon();
for(int i = 0; i < p2.npoints; ++i){
p.addPoint(trans.xToScreen(((Polygon2D.Double)p2).xpoints[i]),trans.yToScreen(((Polygon2D.Double)p2).ypoints[i]));
}
result.add(p);
}
return result;
}
public double getArea(){
return semiGlossArea;
}
public Map<Integer,Double> getBuildingsArea(){
return buildingsArea;
}
public List<GMLBuilding> getBuildingsInArea(){
return buildingsInArea;
}
private Polygon2D getPolygon2DFromEdge(Line2D edge, double space){
Polygon2D result = new Polygon2D.Double();
Point2D start = edge.getP1();
Point2D end = edge.getP2();
double xDif = Math.abs(start.getX()-end.getX());
double yDif = Math.abs(start.getY()-end.getY());
if(xDif == 0){
result.addPoint(start.getX()-space, start.getY());
result.addPoint(start.getX()+space, start.getY());
result.addPoint(end.getX()+space, end.getY());
result.addPoint(end.getX()-space, end.getY());
}else if(yDif == 0){
result.addPoint(start.getX(), start.getY()+space);
result.addPoint(start.getX(), start.getY()-space);
result.addPoint(end.getX(), end.getY()-space);
result.addPoint(end.getX(), end.getY()+space);
}else{
if(xDif > yDif){
//yokonaga
if(start.getX() > end.getX()){
Point2D temp = end;
end = start;
start = temp;
}
if(start.getY() < end.getY()){
///
double ang = Math.atan2(yDif,xDif);
double ySlope = space * Math.cos(ang);
double xSlope = space * Math.sin(ang);
result.addPoint(start.getX()+xSlope, start.getY()-ySlope);
result.addPoint(start.getX()-xSlope, start.getY()+ySlope);
result.addPoint(end.getX()-xSlope, end.getY()+ySlope);
result.addPoint(end.getX()+xSlope, end.getY()-ySlope);
}else{
//¥
double ang = Math.atan2(yDif,xDif);
double ySlope = space * Math.cos(ang);
double xSlope = space * Math.sin(ang);
result.addPoint(start.getX()-xSlope, start.getY()-ySlope);
result.addPoint(start.getX()+xSlope, start.getY()+ySlope);
result.addPoint(end.getX()+xSlope, end.getY()+ySlope);
result.addPoint(end.getX()-xSlope, end.getY()-ySlope);
}
}else{
//tatenaga
if(start.getY() > end.getY()){
Point2D temp = end;
end = start;
start = temp;
}
if(start.getX() < end.getX()){
//¥
double ang = Math.atan2(yDif,xDif);
double ySlope = space * Math.cos(ang);
double xSlope = space * Math.sin(ang);
result.addPoint(start.getX()+xSlope, start.getY()-ySlope);
result.addPoint(start.getX()-xSlope, start.getY()+ySlope);
result.addPoint(end.getX()-xSlope, end.getY()+ySlope);
result.addPoint(end.getX()+xSlope, end.getY()-ySlope);
}else{
///
double ang = Math.atan2(yDif,xDif);
double ySlope = space * Math.cos(ang);
double xSlope = space * Math.sin(ang);
result.addPoint(start.getX()-xSlope, start.getY()-ySlope);
result.addPoint(start.getX()+xSlope, start.getY()+ySlope);
result.addPoint(end.getX()+xSlope, end.getY()+ySlope);
result.addPoint(end.getX()-xSlope, end.getY()-ySlope);
}
}
}
return result;
}
private Polygon2D getPolygon2DFromEdge(GMLDirectedEdge edge, double space){
Polygon2D result = new Polygon2D.Double();
GMLCoordinates start = edge.getStartCoordinates();
GMLCoordinates end = edge.getEndCoordinates();
double xDif = Math.abs(start.getX()-end.getX());
double yDif = Math.abs(start.getY()-end.getY());
if(xDif == 0){
result.addPoint(start.getX()-space, start.getY());
result.addPoint(start.getX()+space, start.getY());
result.addPoint(end.getX()+space, end.getY());
result.addPoint(end.getX()-space, end.getY());
}else if(yDif == 0){
result.addPoint(start.getX(), start.getY()+space);
result.addPoint(start.getX(), start.getY()-space);
result.addPoint(end.getX(), end.getY()-space);
result.addPoint(end.getX(), end.getY()+space);
}else{
if(xDif > yDif){
//yokonaga
if(start.getX() > end.getX()){
GMLCoordinates temp = end;
end = start;
start = temp;
}
if(start.getY() < end.getY()){
///
double ang = Math.atan2(yDif,xDif);
double ySlope = space * Math.cos(ang);
double xSlope = space * Math.sin(ang);
result.addPoint(start.getX()+xSlope, start.getY()-ySlope);
result.addPoint(start.getX()-xSlope, start.getY()+ySlope);
result.addPoint(end.getX()-xSlope, end.getY()+ySlope);
result.addPoint(end.getX()+xSlope, end.getY()-ySlope);
}else{
//¥
double ang = Math.atan2(yDif,xDif);
double ySlope = space * Math.cos(ang);
double xSlope = space * Math.sin(ang);
result.addPoint(start.getX()-xSlope, start.getY()-ySlope);
result.addPoint(start.getX()+xSlope, start.getY()+ySlope);
result.addPoint(end.getX()+xSlope, end.getY()+ySlope);
result.addPoint(end.getX()-xSlope, end.getY()-ySlope);
}
}else{
//tatenaga
if(start.getY() > end.getY()){
GMLCoordinates temp = end;
end = start;
start = temp;
}
if(start.getX() < end.getX()){
//¥
double ang = Math.atan2(yDif,xDif);
double ySlope = space * Math.cos(ang);
double xSlope = space * Math.sin(ang);
result.addPoint(start.getX()+xSlope, start.getY()-ySlope);
result.addPoint(start.getX()-xSlope, start.getY()+ySlope);
result.addPoint(end.getX()-xSlope, end.getY()+ySlope);
result.addPoint(end.getX()+xSlope, end.getY()-ySlope);
}else{
///
double ang = Math.atan2(yDif,xDif);
double ySlope = space * Math.cos(ang);
double xSlope = space * Math.sin(ang);
result.addPoint(start.getX()-xSlope, start.getY()-ySlope);
result.addPoint(start.getX()+xSlope, start.getY()+ySlope);
result.addPoint(end.getX()+xSlope, end.getY()+ySlope);
result.addPoint(end.getX()-xSlope, end.getY()-ySlope);
}
}
}
return result;
}
public Polygon2D getGloss(){
return gloss;
}
public List<List<Integer>> getNeighbourBuildings(){
return neighbourBuildings;
}
public Polygon getPolygon(ScreenTransform trans){
Polygon p = new Polygon();
for(int i = 0; i < gloss.npoints; ++i){
p.addPoint(trans.xToScreen(gloss.xpoints[i]), trans.yToScreen(gloss.ypoints[i]));
}
return p;
}
public boolean setBuilding(GMLBuilding building){
for(GMLDirectedEdge edge : building.getEdges()){
for(GMLCoordinates point : edge.getPoints()){
if(!(gloss.contains(point.getX(), point.getY()))){
return false;
}
}
}
buildingsInArea.add(building);
return true;
}
private class Vector2d
{
public double x;
public double y;
public Vector2d()
{
this.x = 0;
this.y = 0;
}
public Vector2d(Vector2d v)
{
this.x = v.x;
this.y = v.y;
}
public Vector2d(double x, double y)
{
this.x = x;
this.y = y;
}
public Vector2d(double x1, double y1, double x2, double y2)
{
this.x = x2 - x1;
this.y = y2 - y1;
}
public double length()
{
return Math.sqrt(x*x + y*y);
}
public double dot(Vector2d v)
{
return x*v.x + y*v.y;
}
public Vector2d norm()
{
double l = this.length();
return new Vector2d(x/l, y/l);
}
public void normalize()
{
double l = this.length();
this.x /= l;
this.y /= l;
}
public void add(Vector2d v)
{
this.x += v.x;
this.y += v.y;
}
public void mul(double scale)
{
this.x *= scale;
this.y *= scale;
}
public void inverse()
{
this.x *= -1;
this.y *= -1;
}
public double angular(Vector2d v)
{
double denom = this.length() * v.length();
return Math.acos(this.dot(v) /denom);
}
public double projection(Vector2d v)
{
double denom = this.length() * v.length();
return v.length() * this.dot(v) / denom;
}
}
}
```