
apoc.algo.PathFindingUtils Maven / Gradle / Ivy
Go to download
Show more of this group Show more artifacts with this name
Show all versions of apoc-common Show documentation
Show all versions of apoc-common Show documentation
Data types package for Neo4j Procedures
package apoc.algo;
import apoc.path.RelationshipTypeAndDirections;
import org.apache.commons.lang3.tuple.Pair;
import org.neo4j.graphalgo.EstimateEvaluator;
import org.neo4j.graphdb.Direction;
import org.neo4j.graphdb.Node;
import org.neo4j.graphdb.PathExpander;
import org.neo4j.graphdb.PathExpanderBuilder;
import org.neo4j.graphdb.RelationshipType;
import org.neo4j.values.storable.PointValue;
public class PathFindingUtils {
public static class GeoEstimateEvaluatorPointCustom implements EstimateEvaluator {
// -- from org.neo4j.graphalgo.impl.util.GeoEstimateEvaluator
private static final double EARTH_RADIUS = 6371 * 1000; // Meters
private Node cachedGoal;
private final String pointPropertyKey;
private double[] cachedGoalCoordinates;
public GeoEstimateEvaluatorPointCustom(String pointPropertyKey) {
this.pointPropertyKey = pointPropertyKey;
}
@Override
public Double getCost( Node node, Node goal) {
double[] nodeCoordinates = getCoordinates(node);
if ( cachedGoal == null || !cachedGoal.equals( goal ) )
{
cachedGoalCoordinates = getCoordinates(goal);
cachedGoal = goal;
}
return distance(nodeCoordinates[0], nodeCoordinates[1],
cachedGoalCoordinates[0], cachedGoalCoordinates[1] );
}
private static double distance( double latitude1, double longitude1,
double latitude2, double longitude2 ) {
latitude1 = Math.toRadians( latitude1 );
longitude1 = Math.toRadians( longitude1 );
latitude2 = Math.toRadians( latitude2 );
longitude2 = Math.toRadians( longitude2 );
double cLa1 = Math.cos( latitude1 );
double xA = EARTH_RADIUS * cLa1 * Math.cos( longitude1 );
double yA = EARTH_RADIUS * cLa1 * Math.sin( longitude1 );
double zA = EARTH_RADIUS * Math.sin( latitude1 );
double cLa2 = Math.cos( latitude2 );
double xB = EARTH_RADIUS * cLa2 * Math.cos( longitude2 );
double yB = EARTH_RADIUS * cLa2 * Math.sin( longitude2 );
double zB = EARTH_RADIUS * Math.sin( latitude2 );
return Math.sqrt( ( xA - xB ) * ( xA - xB ) + ( yA - yB )
* ( yA - yB ) + ( zA - zB ) * ( zA - zB ) );
}
// -- end from org.neo4j.graphalgo.impl.util.GeoEstimateEvaluator
private double[] getCoordinates(Node node) {
return ((PointValue) node.getProperty(pointPropertyKey)).coordinate();
}
}
public static PathExpander buildPathExpander(String relationshipsAndDirections) {
PathExpanderBuilder builder = PathExpanderBuilder.empty();
for (Pair pair : RelationshipTypeAndDirections
.parse(relationshipsAndDirections)) {
if (pair.getLeft() == null) {
if (pair.getRight() == null) {
builder = PathExpanderBuilder.allTypesAndDirections();
} else {
builder = PathExpanderBuilder.allTypes(pair.getRight());
}
} else {
if (pair.getRight() == null) {
builder = builder.add(pair.getLeft());
} else {
builder = builder.add(pair.getLeft(), pair.getRight());
}
}
}
return builder.build();
}
}
© 2015 - 2025 Weber Informatics LLC | Privacy Policy