Compare commits
211 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
| ccc4607d6d | |||
| 4ec41392f7 | |||
| 5f2b2cd0f7 | |||
| 361e3ca356 | |||
| 13bf4fab32 | |||
| 4b583e8ce9 | |||
| d31c6fe286 | |||
| 79de97d814 | |||
| 1c5d093b59 | |||
| ecff2beafa | |||
| 7e0b19c43d | |||
| 2ebe2faa74 | |||
| aec1451168 | |||
| 38251aa513 | |||
| d92e8ca8d2 | |||
| 2e5876d488 | |||
| 3dddd16ec7 | |||
| 40ff7ad999 | |||
| cb79f769c9 | |||
| e95feff016 | |||
| f65b32c1af | |||
| 46dd9b9887 | |||
| 4445f21e8a | |||
| 00d3676a20 | |||
| 0f7cb12e97 | |||
| 8485e02c00 | |||
| ae7300f9b4 | |||
| fc796539e8 | |||
| 1d8c43b445 | |||
| 58de37e822 | |||
| 7b3a0c5105 | |||
| 592034653c | |||
| 8d9f830c53 | |||
| d8eea0ce0e | |||
| c28c441e77 | |||
| 1391420699 | |||
| c0be751ef4 | |||
| 5e2462e061 | |||
| 5c0eb4772d | |||
| ef8706b4e1 | |||
| acd1919e8d | |||
| 459e2a322b | |||
| e62caf33aa | |||
| 72fd0f3d41 | |||
| 032c21c545 | |||
| b391daac6d | |||
| 8cb6959e3f | |||
| 49c817a60e | |||
| 6859b53155 | |||
| c581563230 | |||
| fc1db35f27 | |||
| 2734a4aee4 | |||
| 172f65969c | |||
| f0dbe0deb9 | |||
| 8f8d81f90c | |||
| 665523bc7e | |||
| 99e8fa70ba | |||
| 4c1d7c9d73 | |||
| d1cc8e7ad7 | |||
| 7629e44e4c | |||
| b62f6a6141 | |||
| 10d7a2396c | |||
| 007eced326 | |||
| 1128270d4b | |||
| c7d889bf9e | |||
| 7cb585c1a1 | |||
| 75157221b2 | |||
| 9807520ef0 | |||
| c658ee5c78 | |||
| cbfbcdcff5 | |||
| 9a0581ea7f | |||
| 60c268ddd6 | |||
| 0361e0204a | |||
| 2da427134b | |||
| 4fce0dadcf | |||
| 288c241fb4 | |||
| f3e3eda69e | |||
| 0f4dd8103d | |||
| 86ee05ee5e | |||
| 3b9c6a6465 | |||
| 8e73a4a19d | |||
| 428bb36ec6 | |||
| 0a24df6bd0 | |||
| d3ca080729 | |||
| 7658031784 | |||
| 710e74219a | |||
| 0249bed53a | |||
| 9d14f81b79 | |||
| a7c683a83c | |||
| 16631bf454 | |||
| 3c563f7073 | |||
| 344bdbb707 | |||
| a0256dfc60 | |||
| b131f27eb9 | |||
| 0d9b70552e | |||
| ea1a89290a | |||
| 59f1679d37 | |||
| 5121983218 | |||
| 0d7141ce5b | |||
| b4b753ce2e | |||
| 4f666e4d53 | |||
| 874a988527 | |||
| 51c79f9784 | |||
| 4d19811026 | |||
| d1454075ab | |||
| becb6cf5bf | |||
| a6f34d2044 | |||
| 7300024e13 | |||
| 282800e6b1 | |||
| e938bd3481 | |||
| 9b501276fb | |||
| 90d191f5f8 | |||
| f452e7f9d2 | |||
| 1d25f41122 | |||
| 5556785804 | |||
| 22ce4c24fb | |||
| d4d2d127d1 | |||
| 3c28932862 | |||
| 7e9177cb3c | |||
| f692103c81 | |||
| 5a1dfe9b89 | |||
| 7175180dc9 | |||
| f95d1fa8ba | |||
| 7b57068f6f | |||
| d79eac3e26 | |||
| 27c255c874 | |||
| bdc611b23a | |||
| 4cddf0bf5d | |||
| 462d4c99cc | |||
| 94a2188090 | |||
| ebcdcb5f00 | |||
| f9e780ed67 | |||
| 18f8ce69cd | |||
| dce665f14e | |||
| 80046b646b | |||
| 06ddceeac0 | |||
| b7ea1dfcd0 | |||
| 6d9598cd4c | |||
| 60c9701c3f | |||
| 2a8644b72c | |||
| b6e469abd1 | |||
| 004c237085 | |||
| 398e3bdf82 | |||
| 958350af82 | |||
| 2d677a8af9 | |||
| 05a79f5b55 | |||
| ac9566d3d7 | |||
| 8b7bf94aae | |||
| c4e785e523 | |||
| 2f6f883f7f | |||
| d071e92a1c | |||
| b18b4072e1 | |||
| 0a2898da17 | |||
| 73fb596973 | |||
| c3f9dc7400 | |||
| c75ce210ea | |||
| ffca6d8ba5 | |||
| 1ec35befc8 | |||
| 6080eaebbd | |||
| 41ea339053 | |||
| bec585e382 | |||
| 2cc8ae875a | |||
| db8252e650 | |||
| e3cb26a1c4 | |||
| 44036ae26d | |||
| 5b5f871a6e | |||
| 9a8f9cae6d | |||
| 8f804581c0 | |||
| e26ef17545 | |||
| 800bb223b5 | |||
| 75606f2100 | |||
| a28928e6ca | |||
| 8700007025 | |||
| 520f7fa2de | |||
| 096208a154 | |||
| 27caab69ec | |||
| 3fe2b587cb | |||
| c791188811 | |||
| b227c90c18 | |||
| 8a5538356b | |||
| b257c881b5 | |||
| 0f5dffb1c3 | |||
| d2bd238274 | |||
| fed700440d | |||
| 32a9d42412 | |||
| efc938d870 | |||
| 369f669227 | |||
| 1c56671f01 | |||
| 4dbc1e0e96 | |||
| 94288843f1 | |||
| b12decc865 | |||
| 0fc944abf3 | |||
| 9f96c98f02 | |||
| 9805b05738 | |||
| 13ed186469 | |||
| 00a43221ac | |||
| edc39112e2 | |||
| 3b727dea99 | |||
| f16b2adec7 | |||
| 7d425aa76f | |||
| 651c07c724 | |||
| 4d27b75897 | |||
| 6f75d68d07 | |||
| ae269e12bb | |||
| 3a48929fe6 | |||
| be970326b6 | |||
| 463511871f | |||
| 002da1e02d | |||
| b095aae5ce | |||
| 511c21029e | |||
| 81b0447024 |
+2
-1
@@ -36,7 +36,7 @@ Thumbs.db
|
|||||||
# build related files #
|
# build related files #
|
||||||
#######################
|
#######################
|
||||||
/build/
|
/build/
|
||||||
/Util/FingerPrint.cpp
|
/Util/finger_print.cpp
|
||||||
/Util/GitDescription.cpp
|
/Util/GitDescription.cpp
|
||||||
/cmake/postinst
|
/cmake/postinst
|
||||||
|
|
||||||
@@ -81,6 +81,7 @@ stxxl.errlog
|
|||||||
/osrm-unlock-all
|
/osrm-unlock-all
|
||||||
/osrm-cli
|
/osrm-cli
|
||||||
/osrm-check-hsgr
|
/osrm-check-hsgr
|
||||||
|
/osrm-springclean
|
||||||
/nohup.out
|
/nohup.out
|
||||||
|
|
||||||
# Sandbox folder #
|
# Sandbox folder #
|
||||||
|
|||||||
+7
-4
@@ -7,15 +7,17 @@ install:
|
|||||||
- sudo apt-add-repository -y ppa:ubuntu-toolchain-r/test
|
- sudo apt-add-repository -y ppa:ubuntu-toolchain-r/test
|
||||||
- sudo add-apt-repository -y ppa:boost-latest/ppa
|
- sudo add-apt-repository -y ppa:boost-latest/ppa
|
||||||
- sudo apt-get update >/dev/null
|
- sudo apt-get update >/dev/null
|
||||||
- sudo apt-get -q install protobuf-compiler libprotoc-dev libprotobuf7 libprotobuf-dev libosmpbf-dev libbz2-dev libstxxl-dev libstxxl1 libxml2-dev libzip-dev lua5.1 liblua5.1-0-dev rubygems libtbb-dev
|
- sudo apt-get -q install protobuf-compiler libprotoc-dev libprotobuf7 libprotobuf-dev libbz2-dev libstxxl-dev libstxxl1 libxml2-dev libzip-dev lua5.1 liblua5.1-0-dev rubygems libtbb-dev
|
||||||
- sudo apt-get -q install g++-4.8
|
- sudo apt-get -q install g++-4.8
|
||||||
- sudo apt-get install libboost1.54-all-dev
|
- sudo apt-get install libboost1.54-all-dev
|
||||||
#luabind
|
# luabind
|
||||||
- curl https://gist.githubusercontent.com/DennisOSRM/f2eb7b948e6fe1ae319e/raw/install-luabind.sh | sudo bash
|
- curl https://gist.githubusercontent.com/DennisOSRM/f2eb7b948e6fe1ae319e/raw/install-luabind.sh | sudo bash
|
||||||
#osmosis
|
# osmosis
|
||||||
- curl -s https://gist.githubusercontent.com/DennisOSRM/803a64a9178ec375069f/raw/ | sudo bash
|
- curl -s https://gist.githubusercontent.com/DennisOSRM/803a64a9178ec375069f/raw/ | sudo bash
|
||||||
#cmake
|
# cmake
|
||||||
- curl -s https://gist.githubusercontent.com/DennisOSRM/5fad9bee5c7f09fd7fc9/raw/ | sudo bash
|
- curl -s https://gist.githubusercontent.com/DennisOSRM/5fad9bee5c7f09fd7fc9/raw/ | sudo bash
|
||||||
|
# osmpbf library
|
||||||
|
- curl -s https://gist.githubusercontent.com/DennisOSRM/13b1b4fe38a57ead850e/raw/install_osmpbf.sh | sudo bash
|
||||||
before_script:
|
before_script:
|
||||||
- rvm use 1.9.3
|
- rvm use 1.9.3
|
||||||
- gem install bundler
|
- gem install bundler
|
||||||
@@ -26,6 +28,7 @@ before_script:
|
|||||||
script:
|
script:
|
||||||
- make -j 2
|
- make -j 2
|
||||||
- make -j 2 tests
|
- make -j 2 tests
|
||||||
|
- ./datastructure-tests
|
||||||
- cd ..
|
- cd ..
|
||||||
- cucumber -p verify
|
- cucumber -p verify
|
||||||
after_script:
|
after_script:
|
||||||
|
|||||||
@@ -1,130 +0,0 @@
|
|||||||
#include "../DataStructures/OriginalEdgeData.h"
|
|
||||||
#include "../DataStructures/QueryNode.h"
|
|
||||||
#include "../DataStructures/SharedMemoryVectorWrapper.h"
|
|
||||||
#include "../DataStructures/StaticRTree.h"
|
|
||||||
#include "../Util/BoostFileSystemFix.h"
|
|
||||||
#include "../DataStructures/EdgeBasedNode.h"
|
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
|
||||||
|
|
||||||
#include <random>
|
|
||||||
|
|
||||||
// Choosen by a fair W20 dice roll (this value is completely arbitrary)
|
|
||||||
constexpr unsigned RANDOM_SEED = 13;
|
|
||||||
constexpr int32_t WORLD_MIN_LAT = -90 * COORDINATE_PRECISION;
|
|
||||||
constexpr int32_t WORLD_MAX_LAT = 90 * COORDINATE_PRECISION;
|
|
||||||
constexpr int32_t WORLD_MIN_LON = -180 * COORDINATE_PRECISION;
|
|
||||||
constexpr int32_t WORLD_MAX_LON = 180 * COORDINATE_PRECISION;
|
|
||||||
|
|
||||||
using RTreeLeaf = EdgeBasedNode;
|
|
||||||
using FixedPointCoordinateListPtr = std::shared_ptr<std::vector<FixedPointCoordinate>>;
|
|
||||||
using BenchStaticRTree = StaticRTree<RTreeLeaf, ShM<FixedPointCoordinate, false>::vector, false>;
|
|
||||||
|
|
||||||
FixedPointCoordinateListPtr LoadCoordinates(const boost::filesystem::path &nodes_file)
|
|
||||||
{
|
|
||||||
boost::filesystem::ifstream nodes_input_stream(nodes_file, std::ios::binary);
|
|
||||||
|
|
||||||
NodeInfo current_node;
|
|
||||||
unsigned number_of_coordinates = 0;
|
|
||||||
nodes_input_stream.read((char *)&number_of_coordinates, sizeof(unsigned));
|
|
||||||
auto coords = std::make_shared<std::vector<FixedPointCoordinate>>(number_of_coordinates);
|
|
||||||
for (unsigned i = 0; i < number_of_coordinates; ++i)
|
|
||||||
{
|
|
||||||
nodes_input_stream.read((char *)¤t_node, sizeof(NodeInfo));
|
|
||||||
coords->at(i) = FixedPointCoordinate(current_node.lat, current_node.lon);
|
|
||||||
BOOST_ASSERT((std::abs(coords->at(i).lat) >> 30) == 0);
|
|
||||||
BOOST_ASSERT((std::abs(coords->at(i).lon) >> 30) == 0);
|
|
||||||
}
|
|
||||||
nodes_input_stream.close();
|
|
||||||
return coords;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Benchmark(BenchStaticRTree &rtree, unsigned num_queries)
|
|
||||||
{
|
|
||||||
std::mt19937 mt_rand(RANDOM_SEED);
|
|
||||||
std::uniform_int_distribution<> lat_udist(WORLD_MIN_LAT, WORLD_MAX_LAT);
|
|
||||||
std::uniform_int_distribution<> lon_udist(WORLD_MIN_LON, WORLD_MAX_LON);
|
|
||||||
std::vector<FixedPointCoordinate> queries;
|
|
||||||
for (unsigned i = 0; i < num_queries; i++)
|
|
||||||
{
|
|
||||||
queries.emplace_back(FixedPointCoordinate(lat_udist(mt_rand), lon_udist(mt_rand)));
|
|
||||||
}
|
|
||||||
|
|
||||||
const unsigned num_results = 5;
|
|
||||||
std::cout << "#### IncrementalFindPhantomNodeForCoordinate : " << num_results
|
|
||||||
<< " phantom nodes"
|
|
||||||
<< "\n";
|
|
||||||
|
|
||||||
TIMER_START(query_phantom);
|
|
||||||
std::vector<PhantomNode> resulting_phantom_node_vector;
|
|
||||||
for (const auto &q : queries)
|
|
||||||
{
|
|
||||||
resulting_phantom_node_vector.clear();
|
|
||||||
rtree.IncrementalFindPhantomNodeForCoordinate(
|
|
||||||
q, resulting_phantom_node_vector, 3, num_results);
|
|
||||||
resulting_phantom_node_vector.clear();
|
|
||||||
rtree.IncrementalFindPhantomNodeForCoordinate(
|
|
||||||
q, resulting_phantom_node_vector, 17, num_results);
|
|
||||||
}
|
|
||||||
TIMER_STOP(query_phantom);
|
|
||||||
|
|
||||||
std::cout << "Took " << TIMER_MSEC(query_phantom) << " msec for " << num_queries << " queries."
|
|
||||||
<< "\n";
|
|
||||||
std::cout << TIMER_MSEC(query_phantom) / ((double)num_queries) << " msec/query."
|
|
||||||
<< "\n";
|
|
||||||
|
|
||||||
std::cout << "#### LocateClosestEndPointForCoordinate"
|
|
||||||
<< "\n";
|
|
||||||
|
|
||||||
TIMER_START(query_endpoint);
|
|
||||||
FixedPointCoordinate result;
|
|
||||||
for (const auto &q : queries)
|
|
||||||
{
|
|
||||||
rtree.LocateClosestEndPointForCoordinate(q, result, 3);
|
|
||||||
}
|
|
||||||
TIMER_STOP(query_endpoint);
|
|
||||||
|
|
||||||
std::cout << "Took " << TIMER_MSEC(query_endpoint) << " msec for " << num_queries << " queries."
|
|
||||||
<< "\n";
|
|
||||||
std::cout << TIMER_MSEC(query_endpoint) / ((double)num_queries) << " msec/query."
|
|
||||||
<< "\n";
|
|
||||||
|
|
||||||
std::cout << "#### FindPhantomNodeForCoordinate"
|
|
||||||
<< "\n";
|
|
||||||
|
|
||||||
TIMER_START(query_phantomnode);
|
|
||||||
for (const auto &q : queries)
|
|
||||||
{
|
|
||||||
PhantomNode phantom;
|
|
||||||
rtree.FindPhantomNodeForCoordinate(q, phantom, 3);
|
|
||||||
}
|
|
||||||
TIMER_STOP(query_phantomnode);
|
|
||||||
|
|
||||||
std::cout << "Took " << TIMER_MSEC(query_phantomnode) << " msec for " << num_queries
|
|
||||||
<< " queries."
|
|
||||||
<< "\n";
|
|
||||||
std::cout << TIMER_MSEC(query_phantomnode) / ((double)num_queries) << " msec/query."
|
|
||||||
<< "\n";
|
|
||||||
}
|
|
||||||
|
|
||||||
int main(int argc, char **argv)
|
|
||||||
{
|
|
||||||
if (argc < 4)
|
|
||||||
{
|
|
||||||
std::cout << "./rtree-bench file.ramIndex file.fileIndx file.nodes"
|
|
||||||
<< "\n";
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
const char *ramPath = argv[1];
|
|
||||||
const char *filePath = argv[2];
|
|
||||||
const char *nodesPath = argv[3];
|
|
||||||
|
|
||||||
auto coords = LoadCoordinates(nodesPath);
|
|
||||||
|
|
||||||
BenchStaticRTree rtree(ramPath, filePath, coords);
|
|
||||||
|
|
||||||
Benchmark(rtree, 10000);
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
+44
-29
@@ -1,6 +1,6 @@
|
|||||||
cmake_minimum_required(VERSION 2.8.8)
|
cmake_minimum_required(VERSION 2.8.8)
|
||||||
|
|
||||||
if( CMAKE_SOURCE_DIR STREQUAL CMAKE_BINARY_DIR AND NOT MSVC_IDE )
|
if(CMAKE_SOURCE_DIR STREQUAL CMAKE_BINARY_DIR AND NOT MSVC_IDE)
|
||||||
message(FATAL_ERROR "In-source builds are not allowed.
|
message(FATAL_ERROR "In-source builds are not allowed.
|
||||||
Please create a directory and run cmake from there, passing the path to this source directory as the last argument.
|
Please create a directory and run cmake from there, passing the path to this source directory as the last argument.
|
||||||
This process created the file `CMakeCache.txt' and the directory `CMakeFiles'. Please delete them.")
|
This process created the file `CMakeCache.txt' and the directory `CMakeFiles'. Please delete them.")
|
||||||
@@ -31,17 +31,18 @@ OPTION(WITH_TOOLS "Build OSRM tools" OFF)
|
|||||||
OPTION(BUILD_TOOLS "Build OSRM tools" OFF)
|
OPTION(BUILD_TOOLS "Build OSRM tools" OFF)
|
||||||
|
|
||||||
include_directories(${CMAKE_SOURCE_DIR}/Include/)
|
include_directories(${CMAKE_SOURCE_DIR}/Include/)
|
||||||
|
include_directories(${CMAKE_SOURCE_DIR}/third_party/)
|
||||||
|
|
||||||
add_custom_command(OUTPUT ${CMAKE_SOURCE_DIR}/Util/FingerPrint.cpp FingerPrint.cpp.alwaysbuild
|
add_custom_command(OUTPUT ${CMAKE_SOURCE_DIR}/Util/finger_print.cpp finger_print.cpp.alwaysbuild
|
||||||
COMMAND ${CMAKE_COMMAND} -DSOURCE_DIR=${CMAKE_SOURCE_DIR}
|
COMMAND ${CMAKE_COMMAND} -DSOURCE_DIR=${CMAKE_SOURCE_DIR}
|
||||||
-P ${CMAKE_CURRENT_SOURCE_DIR}/cmake/FingerPrint-Config.cmake
|
-P ${CMAKE_CURRENT_SOURCE_DIR}/cmake/FingerPrint-Config.cmake
|
||||||
DEPENDS
|
DEPENDS
|
||||||
${CMAKE_SOURCE_DIR}/Util/FingerPrint.cpp.in
|
${CMAKE_SOURCE_DIR}/Util/finger_print.cpp.in
|
||||||
COMMENT "Configuring FingerPrint.cpp"
|
COMMENT "Configuring finger_print.cpp"
|
||||||
VERBATIM)
|
VERBATIM)
|
||||||
|
|
||||||
add_custom_target(FingerPrintConfigure DEPENDS ${CMAKE_SOURCE_DIR}/Util/FingerPrint.cpp)
|
add_custom_target(FingerPrintConfigure DEPENDS ${CMAKE_SOURCE_DIR}/Util/finger_print.cpp)
|
||||||
add_custom_target(tests DEPENDS datastructure-tests)
|
add_custom_target(tests DEPENDS datastructure-tests algorithm-tests)
|
||||||
add_custom_target(benchmarks DEPENDS rtree-bench)
|
add_custom_target(benchmarks DEPENDS rtree-bench)
|
||||||
|
|
||||||
set(BOOST_COMPONENTS date_time filesystem iostreams program_options regex system thread unit_test_framework)
|
set(BOOST_COMPONENTS date_time filesystem iostreams program_options regex system thread unit_test_framework)
|
||||||
@@ -50,27 +51,29 @@ configure_file(
|
|||||||
${CMAKE_SOURCE_DIR}/Util/GitDescription.cpp.in
|
${CMAKE_SOURCE_DIR}/Util/GitDescription.cpp.in
|
||||||
${CMAKE_SOURCE_DIR}/Util/GitDescription.cpp
|
${CMAKE_SOURCE_DIR}/Util/GitDescription.cpp
|
||||||
)
|
)
|
||||||
file(GLOB ExtractorGlob Extractor/*.cpp)
|
file(GLOB ExtractorGlob extractor/*.cpp)
|
||||||
file(GLOB ImporterGlob DataStructures/Import*.cpp)
|
file(GLOB ImporterGlob data_structures/import_edge.cpp data_structures/external_memory_node.cpp)
|
||||||
add_library(IMPORT OBJECT ${ImporterGlob})
|
add_library(IMPORT OBJECT ${ImporterGlob})
|
||||||
add_library(LOGGER OBJECT Util/simple_logger.cpp)
|
add_library(LOGGER OBJECT Util/simple_logger.cpp)
|
||||||
|
add_library(PHANTOMNODE OBJECT data_structures/phantom_node.cpp)
|
||||||
|
|
||||||
set(ExtractorSources extractor.cpp ${ExtractorGlob})
|
set(ExtractorSources extract.cpp ${ExtractorGlob})
|
||||||
add_executable(osrm-extract ${ExtractorSources} $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:IMPORT> $<TARGET_OBJECTS:LOGGER>)
|
add_executable(osrm-extract ${ExtractorSources} $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:IMPORT> $<TARGET_OBJECTS:LOGGER>)
|
||||||
|
|
||||||
file(GLOB PrepareGlob Contractor/*.cpp DataStructures/HilbertValue.cpp DataStructures/RestrictionMap.cpp Util/compute_angle.cpp)
|
file(GLOB PrepareGlob contractor/*.cpp data_structures/hilbert_value.cpp data_structures/restriction_map.cpp Util/compute_angle.cpp)
|
||||||
set(PrepareSources prepare.cpp ${PrepareGlob})
|
set(PrepareSources prepare.cpp ${PrepareGlob})
|
||||||
add_executable(osrm-prepare ${PrepareSources} $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:IMPORT> $<TARGET_OBJECTS:LOGGER>)
|
add_executable(osrm-prepare ${PrepareSources} $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:IMPORT> $<TARGET_OBJECTS:LOGGER>)
|
||||||
|
|
||||||
file(GLOB ServerGlob Server/*.cpp)
|
file(GLOB ServerGlob Server/*.cpp)
|
||||||
file(GLOB DescriptorGlob Descriptors/*.cpp)
|
file(GLOB DescriptorGlob descriptors/*.cpp)
|
||||||
file(GLOB DatastructureGlob DataStructures/SearchEngineData.cpp DataStructures/RouteParameters.cpp)
|
file(GLOB DatastructureGlob data_structures/search_engine_data.cpp data_structures/route_parameters.cpp Util/bearing.cpp)
|
||||||
list(REMOVE_ITEM DatastructureGlob DataStructures/Coordinate.cpp)
|
list(REMOVE_ITEM DatastructureGlob data_structures/Coordinate.cpp)
|
||||||
file(GLOB CoordinateGlob DataStructures/Coordinate.cpp)
|
file(GLOB CoordinateGlob data_structures/Coordinate.cpp)
|
||||||
file(GLOB AlgorithmGlob Algorithms/*.cpp)
|
file(GLOB AlgorithmGlob algorithms/*.cpp)
|
||||||
file(GLOB HttpGlob Server/Http/*.cpp)
|
file(GLOB HttpGlob Server/Http/*.cpp)
|
||||||
file(GLOB LibOSRMGlob Library/*.cpp)
|
file(GLOB LibOSRMGlob Library/*.cpp)
|
||||||
file(GLOB DataStructureTestsGlob UnitTests/DataStructures/*.cpp DataStructures/HilbertValue.cpp)
|
file(GLOB DataStructureTestsGlob UnitTests/data_structures/*.cpp data_structures/hilbert_value.cpp)
|
||||||
|
file(GLOB AlgorithmTestsGlob UnitTests/Algorithms/*.cpp)
|
||||||
|
|
||||||
set(
|
set(
|
||||||
OSRMSources
|
OSRMSources
|
||||||
@@ -82,19 +85,20 @@ set(
|
|||||||
${HttpGlob}
|
${HttpGlob}
|
||||||
)
|
)
|
||||||
add_library(COORDINATE OBJECT ${CoordinateGlob})
|
add_library(COORDINATE OBJECT ${CoordinateGlob})
|
||||||
add_library(FINGERPRINT OBJECT Util/FingerPrint.cpp)
|
add_library(FINGERPRINT OBJECT Util/finger_print.cpp)
|
||||||
add_library(GITDESCRIPTION OBJECT Util/GitDescription.cpp)
|
add_library(GITDESCRIPTION OBJECT Util/GitDescription.cpp)
|
||||||
add_library(OSRM ${OSRMSources} $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:LOGGER>)
|
add_library(OSRM ${OSRMSources} $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:LOGGER> $<TARGET_OBJECTS:PHANTOMNODE>)
|
||||||
add_dependencies(FINGERPRINT FingerPrintConfigure)
|
add_dependencies(FINGERPRINT FingerPrintConfigure)
|
||||||
|
|
||||||
add_executable(osrm-routed routed.cpp ${ServerGlob})
|
add_executable(osrm-routed routed.cpp ${ServerGlob})
|
||||||
add_executable(osrm-datastore datastore.cpp $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:LOGGER>)
|
add_executable(osrm-datastore datastore.cpp $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:LOGGER>)
|
||||||
|
|
||||||
# Unit tests
|
# Unit tests
|
||||||
add_executable(datastructure-tests EXCLUDE_FROM_ALL UnitTests/datastructure_tests.cpp ${DataStructureTestsGlob} $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:LOGGER>)
|
add_executable(datastructure-tests EXCLUDE_FROM_ALL UnitTests/datastructure_tests.cpp ${DataStructureTestsGlob} $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:LOGGER> $<TARGET_OBJECTS:PHANTOMNODE>)
|
||||||
|
add_executable(algorithm-tests EXCLUDE_FROM_ALL UnitTests/algorithm_tests.cpp ${AlgorithmTestsGlob} $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:LOGGER> $<TARGET_OBJECTS:PHANTOMNODE>)
|
||||||
|
|
||||||
# Benchmarks
|
# Benchmarks
|
||||||
add_executable(rtree-bench EXCLUDE_FROM_ALL Benchmarks/StaticRTreeBench.cpp $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:LOGGER>)
|
add_executable(rtree-bench EXCLUDE_FROM_ALL benchmarks/static_rtree.cpp $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:LOGGER> $<TARGET_OBJECTS:PHANTOMNODE>)
|
||||||
|
|
||||||
# Check the release mode
|
# Check the release mode
|
||||||
if(NOT CMAKE_BUILD_TYPE MATCHES Debug)
|
if(NOT CMAKE_BUILD_TYPE MATCHES Debug)
|
||||||
@@ -152,6 +156,9 @@ elseif("${CMAKE_CXX_COMPILER_ID}" STREQUAL "MSVC")
|
|||||||
add_definitions(-DNOMINMAX) # avoid min and max macros that can break compilation
|
add_definitions(-DNOMINMAX) # avoid min and max macros that can break compilation
|
||||||
add_definitions(-D_USE_MATH_DEFINES) # define M_PI
|
add_definitions(-D_USE_MATH_DEFINES) # define M_PI
|
||||||
add_definitions(-D_WIN32_WINNT=0x0501)
|
add_definitions(-D_WIN32_WINNT=0x0501)
|
||||||
|
add_definitions(-DXML_STATIC)
|
||||||
|
find_library(ws2_32_LIBRARY_PATH ws2_32)
|
||||||
|
target_link_libraries(osrm-extract wsock32 ws2_32)
|
||||||
endif()
|
endif()
|
||||||
|
|
||||||
# Activate C++11
|
# Activate C++11
|
||||||
@@ -194,6 +201,7 @@ target_link_libraries(osrm-prepare ${Boost_LIBRARIES})
|
|||||||
target_link_libraries(osrm-routed ${Boost_LIBRARIES} ${OPTIONAL_SOCKET_LIBS} OSRM)
|
target_link_libraries(osrm-routed ${Boost_LIBRARIES} ${OPTIONAL_SOCKET_LIBS} OSRM)
|
||||||
target_link_libraries(osrm-datastore ${Boost_LIBRARIES})
|
target_link_libraries(osrm-datastore ${Boost_LIBRARIES})
|
||||||
target_link_libraries(datastructure-tests ${Boost_LIBRARIES})
|
target_link_libraries(datastructure-tests ${Boost_LIBRARIES})
|
||||||
|
target_link_libraries(algorithm-tests ${Boost_LIBRARIES} ${OPTIONAL_SOCKET_LIBS} OSRM)
|
||||||
target_link_libraries(rtree-bench ${Boost_LIBRARIES})
|
target_link_libraries(rtree-bench ${Boost_LIBRARIES})
|
||||||
|
|
||||||
find_package(Threads REQUIRED)
|
find_package(Threads REQUIRED)
|
||||||
@@ -202,6 +210,7 @@ target_link_libraries(osrm-datastore ${CMAKE_THREAD_LIBS_INIT})
|
|||||||
target_link_libraries(osrm-prepare ${CMAKE_THREAD_LIBS_INIT})
|
target_link_libraries(osrm-prepare ${CMAKE_THREAD_LIBS_INIT})
|
||||||
target_link_libraries(OSRM ${CMAKE_THREAD_LIBS_INIT})
|
target_link_libraries(OSRM ${CMAKE_THREAD_LIBS_INIT})
|
||||||
target_link_libraries(datastructure-tests ${CMAKE_THREAD_LIBS_INIT})
|
target_link_libraries(datastructure-tests ${CMAKE_THREAD_LIBS_INIT})
|
||||||
|
target_link_libraries(algorithm-tests ${CMAKE_THREAD_LIBS_INIT})
|
||||||
target_link_libraries(rtree-bench ${CMAKE_THREAD_LIBS_INIT})
|
target_link_libraries(rtree-bench ${CMAKE_THREAD_LIBS_INIT})
|
||||||
|
|
||||||
find_package(TBB REQUIRED)
|
find_package(TBB REQUIRED)
|
||||||
@@ -213,6 +222,7 @@ target_link_libraries(osrm-extract ${TBB_LIBRARIES})
|
|||||||
target_link_libraries(osrm-prepare ${TBB_LIBRARIES})
|
target_link_libraries(osrm-prepare ${TBB_LIBRARIES})
|
||||||
target_link_libraries(osrm-routed ${TBB_LIBRARIES})
|
target_link_libraries(osrm-routed ${TBB_LIBRARIES})
|
||||||
target_link_libraries(datastructure-tests ${TBB_LIBRARIES})
|
target_link_libraries(datastructure-tests ${TBB_LIBRARIES})
|
||||||
|
target_link_libraries(algorithm-tests ${TBB_LIBRARIES})
|
||||||
target_link_libraries(rtree-bench ${TBB_LIBRARIES})
|
target_link_libraries(rtree-bench ${TBB_LIBRARIES})
|
||||||
include_directories(${TBB_INCLUDE_DIR})
|
include_directories(${TBB_INCLUDE_DIR})
|
||||||
|
|
||||||
@@ -232,9 +242,9 @@ else()
|
|||||||
endif()
|
endif()
|
||||||
include_directories(${LUA_INCLUDE_DIR})
|
include_directories(${LUA_INCLUDE_DIR})
|
||||||
|
|
||||||
find_package(LibXml2 REQUIRED)
|
find_package(EXPAT REQUIRED)
|
||||||
include_directories(${LIBXML2_INCLUDE_DIR})
|
include_directories(${EXPAT_INCLUDE_DIRS})
|
||||||
target_link_libraries(osrm-extract ${LIBXML2_LIBRARIES})
|
target_link_libraries(osrm-extract ${EXPAT_LIBRARIES})
|
||||||
|
|
||||||
find_package( STXXL REQUIRED )
|
find_package( STXXL REQUIRED )
|
||||||
include_directories(${STXXL_INCLUDE_DIR})
|
include_directories(${STXXL_INCLUDE_DIR})
|
||||||
@@ -242,6 +252,11 @@ target_link_libraries(OSRM ${STXXL_LIBRARY})
|
|||||||
target_link_libraries(osrm-extract ${STXXL_LIBRARY})
|
target_link_libraries(osrm-extract ${STXXL_LIBRARY})
|
||||||
target_link_libraries(osrm-prepare ${STXXL_LIBRARY})
|
target_link_libraries(osrm-prepare ${STXXL_LIBRARY})
|
||||||
|
|
||||||
|
if(MINGW)
|
||||||
|
# STXXL needs OpenMP library
|
||||||
|
target_link_libraries(osrm-extract gomp)
|
||||||
|
endif()
|
||||||
|
|
||||||
find_package( OSMPBF REQUIRED )
|
find_package( OSMPBF REQUIRED )
|
||||||
include_directories(${OSMPBF_INCLUDE_DIR})
|
include_directories(${OSMPBF_INCLUDE_DIR})
|
||||||
target_link_libraries(osrm-extract ${OSMPBF_LIBRARY})
|
target_link_libraries(osrm-extract ${OSMPBF_LIBRARY})
|
||||||
@@ -265,7 +280,7 @@ if(WITH_TOOLS OR BUILD_TOOLS)
|
|||||||
message(STATUS "Activating OSRM internal tools")
|
message(STATUS "Activating OSRM internal tools")
|
||||||
find_package(GDAL)
|
find_package(GDAL)
|
||||||
if(GDAL_FOUND)
|
if(GDAL_FOUND)
|
||||||
add_executable(osrm-components Tools/components.cpp $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:IMPORT> $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:LOGGER>)
|
add_executable(osrm-components tools/components.cpp $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:IMPORT> $<TARGET_OBJECTS:COORDINATE> $<TARGET_OBJECTS:LOGGER>)
|
||||||
target_link_libraries(osrm-components ${TBB_LIBRARIES})
|
target_link_libraries(osrm-components ${TBB_LIBRARIES})
|
||||||
include_directories(${GDAL_INCLUDE_DIR})
|
include_directories(${GDAL_INCLUDE_DIR})
|
||||||
target_link_libraries(
|
target_link_libraries(
|
||||||
@@ -275,19 +290,19 @@ if(WITH_TOOLS OR BUILD_TOOLS)
|
|||||||
else()
|
else()
|
||||||
message(FATAL_ERROR "libgdal and/or development headers not found")
|
message(FATAL_ERROR "libgdal and/or development headers not found")
|
||||||
endif()
|
endif()
|
||||||
add_executable(osrm-cli Tools/simpleclient.cpp $<TARGET_OBJECTS:LOGGER>)
|
add_executable(osrm-cli tools/simpleclient.cpp $<TARGET_OBJECTS:LOGGER>)
|
||||||
target_link_libraries(osrm-cli ${Boost_LIBRARIES} ${OPTIONAL_SOCKET_LIBS} OSRM)
|
target_link_libraries(osrm-cli ${Boost_LIBRARIES} ${OPTIONAL_SOCKET_LIBS} OSRM)
|
||||||
target_link_libraries(osrm-cli ${TBB_LIBRARIES})
|
target_link_libraries(osrm-cli ${TBB_LIBRARIES})
|
||||||
add_executable(osrm-io-benchmark Tools/io-benchmark.cpp $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:LOGGER>)
|
add_executable(osrm-io-benchmark tools/io-benchmark.cpp $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:LOGGER>)
|
||||||
target_link_libraries(osrm-io-benchmark ${Boost_LIBRARIES})
|
target_link_libraries(osrm-io-benchmark ${Boost_LIBRARIES})
|
||||||
add_executable(osrm-unlock-all Tools/unlock_all_mutexes.cpp $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:LOGGER>)
|
add_executable(osrm-unlock-all tools/unlock_all_mutexes.cpp $<TARGET_OBJECTS:GITDESCRIPTION> $<TARGET_OBJECTS:LOGGER>)
|
||||||
target_link_libraries(osrm-unlock-all ${Boost_LIBRARIES} ${CMAKE_THREAD_LIBS_INIT})
|
target_link_libraries(osrm-unlock-all ${Boost_LIBRARIES} ${CMAKE_THREAD_LIBS_INIT})
|
||||||
if(UNIX AND NOT APPLE)
|
if(UNIX AND NOT APPLE)
|
||||||
target_link_libraries(osrm-unlock-all rt)
|
target_link_libraries(osrm-unlock-all rt)
|
||||||
endif()
|
endif()
|
||||||
add_executable(osrm-check-hsgr Tools/check-hsgr.cpp $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:LOGGER>)
|
add_executable(osrm-check-hsgr tools/check-hsgr.cpp $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:LOGGER>)
|
||||||
target_link_libraries(osrm-check-hsgr ${Boost_LIBRARIES})
|
target_link_libraries(osrm-check-hsgr ${Boost_LIBRARIES})
|
||||||
add_executable(osrm-springclean Tools/springclean.cpp $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:LOGGER> $<TARGET_OBJECTS:GITDESCRIPTION>)
|
add_executable(osrm-springclean tools/springclean.cpp $<TARGET_OBJECTS:FINGERPRINT> $<TARGET_OBJECTS:LOGGER> $<TARGET_OBJECTS:GITDESCRIPTION>)
|
||||||
target_link_libraries(osrm-springclean ${Boost_LIBRARIES})
|
target_link_libraries(osrm-springclean ${Boost_LIBRARIES})
|
||||||
|
|
||||||
install(TARGETS osrm-cli DESTINATION bin)
|
install(TARGETS osrm-cli DESTINATION bin)
|
||||||
|
|||||||
@@ -1,3 +0,0 @@
|
|||||||
The javascript based web client is a seperate project available at
|
|
||||||
|
|
||||||
https://github.com/DennisSchiefer/Project-OSRM-Web
|
|
||||||
@@ -1,140 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "BaseParser.h"
|
|
||||||
#include "ExtractionWay.h"
|
|
||||||
#include "ScriptingEnvironment.h"
|
|
||||||
|
|
||||||
#include "../DataStructures/ImportNode.h"
|
|
||||||
#include "../Util/LuaUtil.h"
|
|
||||||
#include "../Util/OSRMException.h"
|
|
||||||
#include "../Util/simple_logger.hpp"
|
|
||||||
|
|
||||||
#include <boost/algorithm/string.hpp>
|
|
||||||
#include <boost/algorithm/string/regex.hpp>
|
|
||||||
#include <boost/ref.hpp>
|
|
||||||
#include <boost/regex.hpp>
|
|
||||||
|
|
||||||
BaseParser::BaseParser(ExtractorCallbacks *extractor_callbacks,
|
|
||||||
ScriptingEnvironment &scripting_environment)
|
|
||||||
: extractor_callbacks(extractor_callbacks),
|
|
||||||
lua_state(scripting_environment.getLuaState()),
|
|
||||||
scripting_environment(scripting_environment), use_turn_restrictions(true)
|
|
||||||
{
|
|
||||||
ReadUseRestrictionsSetting();
|
|
||||||
ReadRestrictionExceptions();
|
|
||||||
}
|
|
||||||
|
|
||||||
void BaseParser::ReadUseRestrictionsSetting()
|
|
||||||
{
|
|
||||||
if (0 != luaL_dostring(lua_state, "return use_turn_restrictions\n"))
|
|
||||||
{
|
|
||||||
use_turn_restrictions = false;
|
|
||||||
}
|
|
||||||
else if (lua_isboolean(lua_state, -1))
|
|
||||||
{
|
|
||||||
use_turn_restrictions = lua_toboolean(lua_state, -1);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (use_turn_restrictions)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write() << "Using turn restrictions";
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
SimpleLogger().Write() << "Ignoring turn restrictions";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void BaseParser::ReadRestrictionExceptions()
|
|
||||||
{
|
|
||||||
if (lua_function_exists(lua_state, "get_exceptions"))
|
|
||||||
{
|
|
||||||
// get list of turn restriction exceptions
|
|
||||||
luabind::call_function<void>(
|
|
||||||
lua_state, "get_exceptions", boost::ref(restriction_exceptions));
|
|
||||||
const unsigned exception_count = restriction_exceptions.size();
|
|
||||||
SimpleLogger().Write() << "Found " << exception_count
|
|
||||||
<< " exceptions to turn restrictions:";
|
|
||||||
for (const std::string &str : restriction_exceptions)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write() << " " << str;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
SimpleLogger().Write() << "Found no exceptions to turn restrictions";
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void BaseParser::report_errors(lua_State *lua_state, const int status) const
|
|
||||||
{
|
|
||||||
if (0 != status)
|
|
||||||
{
|
|
||||||
std::cerr << "-- " << lua_tostring(lua_state, -1) << std::endl;
|
|
||||||
lua_pop(lua_state, 1); // remove error message
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
void BaseParser::ParseNodeInLua(ImportNode &node, lua_State *local_lua_state)
|
|
||||||
{
|
|
||||||
luabind::call_function<void>(local_lua_state, "node_function", boost::ref(node));
|
|
||||||
}
|
|
||||||
|
|
||||||
void BaseParser::ParseWayInLua(ExtractionWay &way, lua_State *local_lua_state)
|
|
||||||
{
|
|
||||||
luabind::call_function<void>(local_lua_state, "way_function", boost::ref(way));
|
|
||||||
}
|
|
||||||
|
|
||||||
bool BaseParser::ShouldIgnoreRestriction(const std::string &except_tag_string) const
|
|
||||||
{
|
|
||||||
// should this restriction be ignored? yes if there's an overlap between:
|
|
||||||
// a) the list of modes in the except tag of the restriction
|
|
||||||
// (except_tag_string), eg: except=bus;bicycle
|
|
||||||
// b) the lua profile defines a hierachy of modes,
|
|
||||||
// eg: [access, vehicle, bicycle]
|
|
||||||
|
|
||||||
if (except_tag_string.empty())
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Be warned, this is quadratic work here, but we assume that
|
|
||||||
// only a few exceptions are actually defined.
|
|
||||||
std::vector<std::string> exceptions;
|
|
||||||
boost::algorithm::split_regex(exceptions, except_tag_string, boost::regex("[;][ ]*"));
|
|
||||||
for (std::string ¤t_string : exceptions)
|
|
||||||
{
|
|
||||||
const auto string_iterator =
|
|
||||||
std::find(restriction_exceptions.begin(), restriction_exceptions.end(), current_string);
|
|
||||||
if (restriction_exceptions.end() != string_iterator)
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
@@ -1,302 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "Extractor.h"
|
|
||||||
|
|
||||||
#include "ExtractorCallbacks.h"
|
|
||||||
#include "ExtractionContainers.h"
|
|
||||||
#include "PBFParser.h"
|
|
||||||
#include "ScriptingEnvironment.h"
|
|
||||||
#include "XMLParser.h"
|
|
||||||
|
|
||||||
#include "../Util/GitDescription.h"
|
|
||||||
#include "../Util/IniFileUtil.h"
|
|
||||||
#include "../Util/OSRMException.h"
|
|
||||||
#include "../Util/simple_logger.hpp"
|
|
||||||
#include "../Util/TimingUtil.h"
|
|
||||||
#include "../typedefs.h"
|
|
||||||
|
|
||||||
#include <boost/program_options.hpp>
|
|
||||||
|
|
||||||
#include <tbb/task_scheduler_init.h>
|
|
||||||
|
|
||||||
#include <cstdlib>
|
|
||||||
|
|
||||||
#include <chrono>
|
|
||||||
#include <fstream>
|
|
||||||
#include <iostream>
|
|
||||||
#include <thread>
|
|
||||||
#include <unordered_map>
|
|
||||||
|
|
||||||
Extractor::Extractor() : requested_num_threads(0), file_has_pbf_format(false)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
Extractor::~Extractor() {}
|
|
||||||
|
|
||||||
bool Extractor::ParseArguments(int argc, char *argv[])
|
|
||||||
{
|
|
||||||
// declare a group of options that will be allowed only on command line
|
|
||||||
boost::program_options::options_description generic_options("Options");
|
|
||||||
generic_options.add_options()("version,v", "Show version")("help,h", "Show this help message")(
|
|
||||||
"config,c",
|
|
||||||
boost::program_options::value<boost::filesystem::path>(&config_file_path)
|
|
||||||
->default_value("extractor.ini"),
|
|
||||||
"Path to a configuration file.");
|
|
||||||
|
|
||||||
// declare a group of options that will be allowed both on command line and in config file
|
|
||||||
boost::program_options::options_description config_options("Configuration");
|
|
||||||
config_options.add_options()("profile,p",
|
|
||||||
boost::program_options::value<boost::filesystem::path>(
|
|
||||||
&profile_path)->default_value("profile.lua"),
|
|
||||||
"Path to LUA routing profile")(
|
|
||||||
"threads,t",
|
|
||||||
boost::program_options::value<unsigned int>(&requested_num_threads)
|
|
||||||
->default_value(tbb::task_scheduler_init::default_num_threads()),
|
|
||||||
"Number of threads to use");
|
|
||||||
|
|
||||||
// hidden options, will be allowed both on command line and in config file, but will not be
|
|
||||||
// shown to the user
|
|
||||||
boost::program_options::options_description hidden_options("Hidden options");
|
|
||||||
hidden_options.add_options()(
|
|
||||||
"input,i",
|
|
||||||
boost::program_options::value<boost::filesystem::path>(&input_path),
|
|
||||||
"Input file in .osm, .osm.bz2 or .osm.pbf format");
|
|
||||||
|
|
||||||
// positional option
|
|
||||||
boost::program_options::positional_options_description positional_options;
|
|
||||||
positional_options.add("input", 1);
|
|
||||||
|
|
||||||
// combine above options for parsing
|
|
||||||
boost::program_options::options_description cmdline_options;
|
|
||||||
cmdline_options.add(generic_options).add(config_options).add(hidden_options);
|
|
||||||
|
|
||||||
boost::program_options::options_description config_file_options;
|
|
||||||
config_file_options.add(config_options).add(hidden_options);
|
|
||||||
|
|
||||||
boost::program_options::options_description visible_options(
|
|
||||||
boost::filesystem::basename(argv[0]) + " <input.osm/.osm.bz2/.osm.pbf> [options]");
|
|
||||||
visible_options.add(generic_options).add(config_options);
|
|
||||||
|
|
||||||
// parse command line options
|
|
||||||
boost::program_options::variables_map option_variables;
|
|
||||||
boost::program_options::store(boost::program_options::command_line_parser(argc, argv)
|
|
||||||
.options(cmdline_options)
|
|
||||||
.positional(positional_options)
|
|
||||||
.run(),
|
|
||||||
option_variables);
|
|
||||||
|
|
||||||
if (option_variables.count("version"))
|
|
||||||
{
|
|
||||||
SimpleLogger().Write() << g_GIT_DESCRIPTION;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (option_variables.count("help"))
|
|
||||||
{
|
|
||||||
SimpleLogger().Write() << visible_options;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
boost::program_options::notify(option_variables);
|
|
||||||
|
|
||||||
// parse config file
|
|
||||||
if (boost::filesystem::is_regular_file(config_file_path))
|
|
||||||
{
|
|
||||||
SimpleLogger().Write() << "Reading options from: " << config_file_path.string();
|
|
||||||
std::string ini_file_contents = ReadIniFileAndLowerContents(config_file_path);
|
|
||||||
std::stringstream config_stream(ini_file_contents);
|
|
||||||
boost::program_options::store(parse_config_file(config_stream, config_file_options),
|
|
||||||
option_variables);
|
|
||||||
boost::program_options::notify(option_variables);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!option_variables.count("input"))
|
|
||||||
{
|
|
||||||
SimpleLogger().Write() << visible_options;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
void Extractor::GenerateOutputFilesNames()
|
|
||||||
{
|
|
||||||
output_file_name = input_path.string();
|
|
||||||
restriction_file_name = input_path.string();
|
|
||||||
std::string::size_type pos = output_file_name.find(".osm.bz2");
|
|
||||||
if (pos == std::string::npos)
|
|
||||||
{
|
|
||||||
pos = output_file_name.find(".osm.pbf");
|
|
||||||
if (pos != std::string::npos)
|
|
||||||
{
|
|
||||||
file_has_pbf_format = true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
pos = output_file_name.find(".osm.xml");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (pos == std::string::npos)
|
|
||||||
{
|
|
||||||
pos = output_file_name.find(".pbf");
|
|
||||||
if (pos != std::string::npos)
|
|
||||||
{
|
|
||||||
file_has_pbf_format = true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (pos == std::string::npos)
|
|
||||||
{
|
|
||||||
pos = output_file_name.find(".osm");
|
|
||||||
if (pos == std::string::npos)
|
|
||||||
{
|
|
||||||
output_file_name.append(".osrm");
|
|
||||||
restriction_file_name.append(".osrm.restrictions");
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
output_file_name.replace(pos, 5, ".osrm");
|
|
||||||
restriction_file_name.replace(pos, 5, ".osrm.restrictions");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
output_file_name.replace(pos, 8, ".osrm");
|
|
||||||
restriction_file_name.replace(pos, 8, ".osrm.restrictions");
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int Extractor::Run(int argc, char *argv[])
|
|
||||||
{
|
|
||||||
try
|
|
||||||
{
|
|
||||||
LogPolicy::GetInstance().Unmute();
|
|
||||||
|
|
||||||
TIMER_START(extracting);
|
|
||||||
|
|
||||||
if (!ParseArguments(argc, argv))
|
|
||||||
return 0;
|
|
||||||
|
|
||||||
if (1 > requested_num_threads)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << "Number of threads must be 1 or larger";
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!boost::filesystem::is_regular_file(input_path))
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << "Input file " << input_path.string()
|
|
||||||
<< " not found!";
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!boost::filesystem::is_regular_file(profile_path))
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << "Profile " << profile_path.string()
|
|
||||||
<< " not found!";
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
const unsigned recommended_num_threads = tbb::task_scheduler_init::default_num_threads();
|
|
||||||
|
|
||||||
SimpleLogger().Write() << "Input file: " << input_path.filename().string();
|
|
||||||
SimpleLogger().Write() << "Profile: " << profile_path.filename().string();
|
|
||||||
SimpleLogger().Write() << "Threads: " << requested_num_threads;
|
|
||||||
if (recommended_num_threads != requested_num_threads)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << "The recommended number of threads is "
|
|
||||||
<< recommended_num_threads
|
|
||||||
<< "! This setting may have performance side-effects.";
|
|
||||||
}
|
|
||||||
|
|
||||||
tbb::task_scheduler_init init(requested_num_threads);
|
|
||||||
|
|
||||||
/*** Setup Scripting Environment ***/
|
|
||||||
ScriptingEnvironment scripting_environment(profile_path.string().c_str());
|
|
||||||
|
|
||||||
GenerateOutputFilesNames();
|
|
||||||
|
|
||||||
std::unordered_map<std::string, NodeID> string_map;
|
|
||||||
ExtractionContainers extraction_containers;
|
|
||||||
|
|
||||||
string_map[""] = 0;
|
|
||||||
auto extractor_callbacks = new ExtractorCallbacks(extraction_containers, string_map);
|
|
||||||
BaseParser *parser;
|
|
||||||
if (file_has_pbf_format)
|
|
||||||
{
|
|
||||||
parser = new PBFParser(input_path.string().c_str(),
|
|
||||||
extractor_callbacks,
|
|
||||||
scripting_environment,
|
|
||||||
requested_num_threads);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
parser = new XMLParser(input_path.string().c_str(),
|
|
||||||
extractor_callbacks,
|
|
||||||
scripting_environment);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!parser->ReadHeader())
|
|
||||||
{
|
|
||||||
throw OSRMException("Parser not initialized!");
|
|
||||||
}
|
|
||||||
|
|
||||||
SimpleLogger().Write() << "Parsing in progress..";
|
|
||||||
TIMER_START(parsing);
|
|
||||||
|
|
||||||
parser->Parse();
|
|
||||||
delete parser;
|
|
||||||
delete extractor_callbacks;
|
|
||||||
|
|
||||||
TIMER_STOP(parsing);
|
|
||||||
SimpleLogger().Write() << "Parsing finished after " << TIMER_SEC(parsing) << " seconds";
|
|
||||||
|
|
||||||
if (extraction_containers.all_edges_list.empty())
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << "The input data is empty, exiting.";
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
|
|
||||||
extraction_containers.PrepareData(output_file_name, restriction_file_name);
|
|
||||||
|
|
||||||
TIMER_STOP(extracting);
|
|
||||||
SimpleLogger().Write() << "extraction finished after " << TIMER_SEC(extracting) << "s";
|
|
||||||
SimpleLogger().Write() << "To prepare the data for routing, run: "
|
|
||||||
<< "./osrm-prepare " << output_file_name << std::endl;
|
|
||||||
}
|
|
||||||
catch (boost::program_options::too_many_positional_options_error &)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << "Only one input file can be specified";
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
catch (std::exception &e)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << e.what();
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
@@ -1,36 +0,0 @@
|
|||||||
#ifndef EXTRACTOR_H_
|
|
||||||
#define EXTRACTOR_H_
|
|
||||||
|
|
||||||
#include <boost/filesystem.hpp>
|
|
||||||
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
class ExtractorCallbacks;
|
|
||||||
|
|
||||||
/** \brief Class of 'extract' utility. */
|
|
||||||
class Extractor
|
|
||||||
{
|
|
||||||
protected:
|
|
||||||
unsigned requested_num_threads;
|
|
||||||
boost::filesystem::path config_file_path;
|
|
||||||
boost::filesystem::path input_path;
|
|
||||||
boost::filesystem::path profile_path;
|
|
||||||
|
|
||||||
std::string output_file_name;
|
|
||||||
std::string restriction_file_name;
|
|
||||||
bool file_has_pbf_format;
|
|
||||||
|
|
||||||
/** \brief Parses "extractor's" command line arguments */
|
|
||||||
bool ParseArguments(int argc, char *argv[]);
|
|
||||||
|
|
||||||
/** \brief Parses config file, if present in options */
|
|
||||||
void GenerateOutputFilesNames();
|
|
||||||
|
|
||||||
public:
|
|
||||||
explicit Extractor();
|
|
||||||
Extractor(const Extractor &) = delete;
|
|
||||||
virtual ~Extractor();
|
|
||||||
|
|
||||||
int Run(int argc, char *argv[]);
|
|
||||||
};
|
|
||||||
#endif /* EXTRACTOR_H_ */
|
|
||||||
@@ -1,182 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "ExtractorCallbacks.h"
|
|
||||||
#include "ExtractionContainers.h"
|
|
||||||
#include "ExtractionWay.h"
|
|
||||||
|
|
||||||
#include "../DataStructures/Restriction.h"
|
|
||||||
#include "../DataStructures/ImportNode.h"
|
|
||||||
#include "../Util/simple_logger.hpp"
|
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
|
||||||
|
|
||||||
#include <limits>
|
|
||||||
#include <string>
|
|
||||||
#include <vector>
|
|
||||||
|
|
||||||
ExtractorCallbacks::ExtractorCallbacks(ExtractionContainers &extraction_containers,
|
|
||||||
std::unordered_map<std::string, NodeID> &string_map)
|
|
||||||
: string_map(string_map), external_memory(extraction_containers)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
/** warning: caller needs to take care of synchronization! */
|
|
||||||
void ExtractorCallbacks::ProcessNode(const ExternalMemoryNode &n)
|
|
||||||
{
|
|
||||||
if (n.lat <= 85 * COORDINATE_PRECISION && n.lat >= -85 * COORDINATE_PRECISION)
|
|
||||||
{
|
|
||||||
external_memory.all_nodes_list.push_back(n);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
bool ExtractorCallbacks::ProcessRestriction(const InputRestrictionContainer &restriction)
|
|
||||||
{
|
|
||||||
external_memory.restrictions_list.push_back(restriction);
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
/** warning: caller needs to take care of synchronization! */
|
|
||||||
void ExtractorCallbacks::ProcessWay(ExtractionWay &parsed_way)
|
|
||||||
{
|
|
||||||
if (((0 >= parsed_way.forward_speed) ||
|
|
||||||
(TRAVEL_MODE_INACCESSIBLE == parsed_way.forward_travel_mode)) &&
|
|
||||||
((0 >= parsed_way.backward_speed) ||
|
|
||||||
(TRAVEL_MODE_INACCESSIBLE == parsed_way.backward_travel_mode)) &&
|
|
||||||
(0 >= parsed_way.duration))
|
|
||||||
{ // Only true if the way is specified by the speed profile
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (parsed_way.path.size() <= 1)
|
|
||||||
{ // safe-guard against broken data
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (std::numeric_limits<unsigned>::max() == parsed_way.id)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logDEBUG) << "found bogus way with id: " << parsed_way.id
|
|
||||||
<< " of size " << parsed_way.path.size();
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (0 < parsed_way.duration)
|
|
||||||
{
|
|
||||||
// TODO: iterate all way segments and set duration corresponding to the length of each
|
|
||||||
// segment
|
|
||||||
parsed_way.forward_speed = parsed_way.duration / (parsed_way.path.size() - 1);
|
|
||||||
parsed_way.backward_speed = parsed_way.duration / (parsed_way.path.size() - 1);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (std::numeric_limits<double>::epsilon() >= std::abs(-1. - parsed_way.forward_speed))
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logDEBUG) << "found way with bogus speed, id: " << parsed_way.id;
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Get the unique identifier for the street name
|
|
||||||
const auto &string_map_iterator = string_map.find(parsed_way.name);
|
|
||||||
if (string_map.end() == string_map_iterator)
|
|
||||||
{
|
|
||||||
parsed_way.nameID = external_memory.name_list.size();
|
|
||||||
external_memory.name_list.push_back(parsed_way.name);
|
|
||||||
string_map.insert(std::make_pair(parsed_way.name, parsed_way.nameID));
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
parsed_way.nameID = string_map_iterator->second;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (TRAVEL_MODE_INACCESSIBLE == parsed_way.forward_travel_mode)
|
|
||||||
{
|
|
||||||
std::reverse(parsed_way.path.begin(), parsed_way.path.end());
|
|
||||||
parsed_way.forward_travel_mode = parsed_way.backward_travel_mode;
|
|
||||||
parsed_way.backward_travel_mode = TRAVEL_MODE_INACCESSIBLE;
|
|
||||||
}
|
|
||||||
|
|
||||||
const bool split_edge =
|
|
||||||
(parsed_way.forward_speed>0) && (TRAVEL_MODE_INACCESSIBLE != parsed_way.forward_travel_mode) &&
|
|
||||||
(parsed_way.backward_speed>0) && (TRAVEL_MODE_INACCESSIBLE != parsed_way.backward_travel_mode) &&
|
|
||||||
((parsed_way.forward_speed != parsed_way.backward_speed) ||
|
|
||||||
(parsed_way.forward_travel_mode != parsed_way.backward_travel_mode));
|
|
||||||
|
|
||||||
BOOST_ASSERT(parsed_way.forward_travel_mode>0);
|
|
||||||
for (unsigned n = 0; n < (parsed_way.path.size() - 1); ++n)
|
|
||||||
{
|
|
||||||
external_memory.all_edges_list.push_back(InternalExtractorEdge(
|
|
||||||
parsed_way.path[n],
|
|
||||||
parsed_way.path[n + 1],
|
|
||||||
((split_edge || TRAVEL_MODE_INACCESSIBLE == parsed_way.backward_travel_mode) ? ExtractionWay::oneway
|
|
||||||
: ExtractionWay::bidirectional),
|
|
||||||
parsed_way.forward_speed,
|
|
||||||
parsed_way.nameID,
|
|
||||||
parsed_way.roundabout,
|
|
||||||
parsed_way.ignoreInGrid,
|
|
||||||
(0 < parsed_way.duration),
|
|
||||||
parsed_way.isAccessRestricted,
|
|
||||||
parsed_way.forward_travel_mode,
|
|
||||||
split_edge));
|
|
||||||
external_memory.used_node_id_list.push_back(parsed_way.path[n]);
|
|
||||||
}
|
|
||||||
external_memory.used_node_id_list.push_back(parsed_way.path.back());
|
|
||||||
|
|
||||||
// The following information is needed to identify start and end segments of restrictions
|
|
||||||
external_memory.way_start_end_id_list.push_back(
|
|
||||||
WayIDStartAndEndEdge(parsed_way.id,
|
|
||||||
parsed_way.path[0],
|
|
||||||
parsed_way.path[1],
|
|
||||||
parsed_way.path[parsed_way.path.size() - 2],
|
|
||||||
parsed_way.path.back()));
|
|
||||||
|
|
||||||
if (split_edge)
|
|
||||||
{ // Only true if the way should be split
|
|
||||||
BOOST_ASSERT(parsed_way.backward_travel_mode>0);
|
|
||||||
std::reverse(parsed_way.path.begin(), parsed_way.path.end());
|
|
||||||
|
|
||||||
for (std::vector<NodeID>::size_type n = 0; n < parsed_way.path.size() - 1; ++n)
|
|
||||||
{
|
|
||||||
external_memory.all_edges_list.push_back(
|
|
||||||
InternalExtractorEdge(parsed_way.path[n],
|
|
||||||
parsed_way.path[n + 1],
|
|
||||||
ExtractionWay::oneway,
|
|
||||||
parsed_way.backward_speed,
|
|
||||||
parsed_way.nameID,
|
|
||||||
parsed_way.roundabout,
|
|
||||||
parsed_way.ignoreInGrid,
|
|
||||||
(0 < parsed_way.duration),
|
|
||||||
parsed_way.isAccessRestricted,
|
|
||||||
parsed_way.backward_travel_mode,
|
|
||||||
split_edge));
|
|
||||||
}
|
|
||||||
external_memory.way_start_end_id_list.push_back(
|
|
||||||
WayIDStartAndEndEdge(parsed_way.id,
|
|
||||||
parsed_way.path[0],
|
|
||||||
parsed_way.path[1],
|
|
||||||
parsed_way.path[parsed_way.path.size() - 2],
|
|
||||||
parsed_way.path.back()));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
@@ -1,114 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef EXTRACTORSTRUCTS_H_
|
|
||||||
#define EXTRACTORSTRUCTS_H_
|
|
||||||
|
|
||||||
#include "../DataStructures/HashTable.h"
|
|
||||||
#include "../DataStructures/ImportNode.h"
|
|
||||||
#include "../typedefs.h"
|
|
||||||
|
|
||||||
#include <limits>
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
struct ExtractorRelation
|
|
||||||
{
|
|
||||||
ExtractorRelation() : type(unknown) {}
|
|
||||||
enum
|
|
||||||
{ unknown = 0,
|
|
||||||
ferry,
|
|
||||||
turnRestriction } type;
|
|
||||||
HashTable<std::string, std::string> keyVals;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct WayIDStartAndEndEdge
|
|
||||||
{
|
|
||||||
unsigned wayID;
|
|
||||||
NodeID firstStart;
|
|
||||||
NodeID firstTarget;
|
|
||||||
NodeID lastStart;
|
|
||||||
NodeID lastTarget;
|
|
||||||
WayIDStartAndEndEdge()
|
|
||||||
: wayID(std::numeric_limits<unsigned>::max()), firstStart(std::numeric_limits<unsigned>::max()), firstTarget(std::numeric_limits<unsigned>::max()), lastStart(std::numeric_limits<unsigned>::max()),
|
|
||||||
lastTarget(std::numeric_limits<unsigned>::max())
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
explicit WayIDStartAndEndEdge(unsigned w, NodeID fs, NodeID ft, NodeID ls, NodeID lt)
|
|
||||||
: wayID(w), firstStart(fs), firstTarget(ft), lastStart(ls), lastTarget(lt)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
static WayIDStartAndEndEdge min_value()
|
|
||||||
{
|
|
||||||
return WayIDStartAndEndEdge((std::numeric_limits<unsigned>::min)(),
|
|
||||||
(std::numeric_limits<unsigned>::min)(),
|
|
||||||
(std::numeric_limits<unsigned>::min)(),
|
|
||||||
(std::numeric_limits<unsigned>::min)(),
|
|
||||||
(std::numeric_limits<unsigned>::min)());
|
|
||||||
}
|
|
||||||
static WayIDStartAndEndEdge max_value()
|
|
||||||
{
|
|
||||||
return WayIDStartAndEndEdge((std::numeric_limits<unsigned>::max)(),
|
|
||||||
(std::numeric_limits<unsigned>::max)(),
|
|
||||||
(std::numeric_limits<unsigned>::max)(),
|
|
||||||
(std::numeric_limits<unsigned>::max)(),
|
|
||||||
(std::numeric_limits<unsigned>::max)());
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
struct CmpWayByID
|
|
||||||
{
|
|
||||||
using value_type = WayIDStartAndEndEdge;
|
|
||||||
bool operator()(const WayIDStartAndEndEdge &a, const WayIDStartAndEndEdge &b) const
|
|
||||||
{
|
|
||||||
return a.wayID < b.wayID;
|
|
||||||
}
|
|
||||||
value_type max_value() { return WayIDStartAndEndEdge::max_value(); }
|
|
||||||
value_type min_value() { return WayIDStartAndEndEdge::min_value(); }
|
|
||||||
};
|
|
||||||
|
|
||||||
struct Cmp
|
|
||||||
{
|
|
||||||
using value_type = NodeID;
|
|
||||||
bool operator()(const NodeID left, const NodeID right) const { return left < right; }
|
|
||||||
value_type max_value() { return 0xffffffff; }
|
|
||||||
value_type min_value() { return 0x0; }
|
|
||||||
};
|
|
||||||
|
|
||||||
struct CmpNodeByID
|
|
||||||
{
|
|
||||||
using value_type = ExternalMemoryNode;
|
|
||||||
bool operator()(const ExternalMemoryNode &left, const ExternalMemoryNode &right) const
|
|
||||||
{
|
|
||||||
return left.node_id < right.node_id;
|
|
||||||
}
|
|
||||||
value_type max_value() { return ExternalMemoryNode::max_value(); }
|
|
||||||
value_type min_value() { return ExternalMemoryNode::min_value(); }
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif /* EXTRACTORSTRUCTS_H_ */
|
|
||||||
@@ -1,665 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "PBFParser.h"
|
|
||||||
|
|
||||||
#include "ExtractionWay.h"
|
|
||||||
#include "ExtractorCallbacks.h"
|
|
||||||
#include "ScriptingEnvironment.h"
|
|
||||||
|
|
||||||
#include "../DataStructures/HashTable.h"
|
|
||||||
#include "../DataStructures/ImportNode.h"
|
|
||||||
#include "../DataStructures/Restriction.h"
|
|
||||||
#include "../Util/MachineInfo.h"
|
|
||||||
#include "../Util/OSRMException.h"
|
|
||||||
#include "../Util/simple_logger.hpp"
|
|
||||||
#include "../typedefs.h"
|
|
||||||
|
|
||||||
#include <boost/assert.hpp>
|
|
||||||
|
|
||||||
#include <tbb/parallel_for.h>
|
|
||||||
#include <tbb/task_scheduler_init.h>
|
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
|
||||||
|
|
||||||
#include <zlib.h>
|
|
||||||
|
|
||||||
#include <functional>
|
|
||||||
#include <iostream>
|
|
||||||
#include <limits>
|
|
||||||
#include <thread>
|
|
||||||
|
|
||||||
PBFParser::PBFParser(const char *fileName,
|
|
||||||
ExtractorCallbacks *extractor_callbacks,
|
|
||||||
ScriptingEnvironment &scripting_environment,
|
|
||||||
unsigned num_threads)
|
|
||||||
: BaseParser(extractor_callbacks, scripting_environment)
|
|
||||||
{
|
|
||||||
if (0 == num_threads)
|
|
||||||
{
|
|
||||||
num_parser_threads = tbb::task_scheduler_init::default_num_threads();
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
num_parser_threads = num_threads;
|
|
||||||
}
|
|
||||||
|
|
||||||
GOOGLE_PROTOBUF_VERIFY_VERSION;
|
|
||||||
// TODO: What is the bottleneck here? Filling the queue or reading the stuff from disk?
|
|
||||||
// NOTE: With Lua scripting, it is parsing the stuff. I/O is virtually for free.
|
|
||||||
|
|
||||||
// Max 2500 items in queue, hardcoded.
|
|
||||||
thread_data_queue = std::make_shared<ConcurrentQueue<ParserThreadData *>>(2500);
|
|
||||||
input.open(fileName, std::ios::in | std::ios::binary);
|
|
||||||
|
|
||||||
if (!input)
|
|
||||||
{
|
|
||||||
throw OSRMException("pbf file not found.");
|
|
||||||
}
|
|
||||||
|
|
||||||
block_count = 0;
|
|
||||||
group_count = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
PBFParser::~PBFParser()
|
|
||||||
{
|
|
||||||
if (input.is_open())
|
|
||||||
{
|
|
||||||
input.close();
|
|
||||||
}
|
|
||||||
|
|
||||||
// Clean up any leftover ThreadData objects in the queue
|
|
||||||
ParserThreadData *thread_data;
|
|
||||||
while (thread_data_queue->try_pop(thread_data))
|
|
||||||
{
|
|
||||||
delete thread_data;
|
|
||||||
}
|
|
||||||
google::protobuf::ShutdownProtobufLibrary();
|
|
||||||
|
|
||||||
SimpleLogger().Write(logDEBUG) << "parsed " << block_count << " blocks from pbf with "
|
|
||||||
<< group_count << " groups";
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool PBFParser::ReadHeader()
|
|
||||||
{
|
|
||||||
ParserThreadData init_data;
|
|
||||||
/** read Header */
|
|
||||||
if (!readPBFBlobHeader(input, &init_data))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (readBlob(input, &init_data))
|
|
||||||
{
|
|
||||||
if (!init_data.PBFHeaderBlock.ParseFromArray(&(init_data.charBuffer[0]),
|
|
||||||
static_cast<int>(init_data.charBuffer.size())))
|
|
||||||
{
|
|
||||||
std::cerr << "[error] Header not parseable!" << std::endl;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
const auto feature_size = init_data.PBFHeaderBlock.required_features_size();
|
|
||||||
for (int i = 0; i < feature_size; ++i)
|
|
||||||
{
|
|
||||||
const std::string &feature = init_data.PBFHeaderBlock.required_features(i);
|
|
||||||
bool supported = false;
|
|
||||||
if ("OsmSchema-V0.6" == feature)
|
|
||||||
{
|
|
||||||
supported = true;
|
|
||||||
}
|
|
||||||
else if ("DenseNodes" == feature)
|
|
||||||
{
|
|
||||||
supported = true;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!supported)
|
|
||||||
{
|
|
||||||
std::cerr << "[error] required feature not supported: " << feature.data()
|
|
||||||
<< std::endl;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
std::cerr << "[error] blob not loaded!" << std::endl;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void PBFParser::ReadData()
|
|
||||||
{
|
|
||||||
bool keep_running = true;
|
|
||||||
do
|
|
||||||
{
|
|
||||||
ParserThreadData *thread_data = new ParserThreadData();
|
|
||||||
keep_running = readNextBlock(input, thread_data);
|
|
||||||
|
|
||||||
if (keep_running)
|
|
||||||
{
|
|
||||||
thread_data_queue->push(thread_data);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
// No more data to read, parse stops when nullptr encountered
|
|
||||||
thread_data_queue->push(nullptr);
|
|
||||||
delete thread_data;
|
|
||||||
}
|
|
||||||
} while (keep_running);
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void PBFParser::ParseData()
|
|
||||||
{
|
|
||||||
tbb::task_scheduler_init init(num_parser_threads);
|
|
||||||
|
|
||||||
while (true)
|
|
||||||
{
|
|
||||||
ParserThreadData *thread_data;
|
|
||||||
thread_data_queue->wait_and_pop(thread_data);
|
|
||||||
if (nullptr == thread_data)
|
|
||||||
{
|
|
||||||
thread_data_queue->push(nullptr); // Signal end of data for other threads
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
loadBlock(thread_data);
|
|
||||||
|
|
||||||
int group_size = thread_data->PBFprimitiveBlock.primitivegroup_size();
|
|
||||||
for (int i = 0; i < group_size; ++i)
|
|
||||||
{
|
|
||||||
thread_data->currentGroupID = i;
|
|
||||||
loadGroup(thread_data);
|
|
||||||
|
|
||||||
if (thread_data->entityTypeIndicator == TypeNode)
|
|
||||||
{
|
|
||||||
parseNode(thread_data);
|
|
||||||
}
|
|
||||||
if (thread_data->entityTypeIndicator == TypeWay)
|
|
||||||
{
|
|
||||||
parseWay(thread_data);
|
|
||||||
}
|
|
||||||
if (thread_data->entityTypeIndicator == TypeRelation)
|
|
||||||
{
|
|
||||||
parseRelation(thread_data);
|
|
||||||
}
|
|
||||||
if (thread_data->entityTypeIndicator == TypeDenseNode)
|
|
||||||
{
|
|
||||||
parseDenseNode(thread_data);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
delete thread_data;
|
|
||||||
thread_data = nullptr;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool PBFParser::Parse()
|
|
||||||
{
|
|
||||||
// Start the read and parse threads
|
|
||||||
std::thread read_thread(std::bind(&PBFParser::ReadData, this));
|
|
||||||
|
|
||||||
// Open several parse threads that are synchronized before call to
|
|
||||||
std::thread parse_thread(std::bind(&PBFParser::ParseData, this));
|
|
||||||
|
|
||||||
// Wait for the threads to finish
|
|
||||||
read_thread.join();
|
|
||||||
parse_thread.join();
|
|
||||||
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void PBFParser::parseDenseNode(ParserThreadData *thread_data)
|
|
||||||
{
|
|
||||||
const OSMPBF::DenseNodes &dense =
|
|
||||||
thread_data->PBFprimitiveBlock.primitivegroup(thread_data->currentGroupID).dense();
|
|
||||||
int denseTagIndex = 0;
|
|
||||||
int64_t m_lastDenseID = 0;
|
|
||||||
int64_t m_lastDenseLatitude = 0;
|
|
||||||
int64_t m_lastDenseLongitude = 0;
|
|
||||||
|
|
||||||
const int number_of_nodes = dense.id_size();
|
|
||||||
std::vector<ImportNode> extracted_nodes_vector(number_of_nodes);
|
|
||||||
for (int i = 0; i < number_of_nodes; ++i)
|
|
||||||
{
|
|
||||||
m_lastDenseID += dense.id(i);
|
|
||||||
m_lastDenseLatitude += dense.lat(i);
|
|
||||||
m_lastDenseLongitude += dense.lon(i);
|
|
||||||
extracted_nodes_vector[i].node_id = static_cast<NodeID>(m_lastDenseID);
|
|
||||||
extracted_nodes_vector[i].lat = static_cast<int>(
|
|
||||||
COORDINATE_PRECISION *
|
|
||||||
((double)m_lastDenseLatitude * thread_data->PBFprimitiveBlock.granularity() +
|
|
||||||
thread_data->PBFprimitiveBlock.lat_offset()) /
|
|
||||||
NANO);
|
|
||||||
extracted_nodes_vector[i].lon = static_cast<int>(
|
|
||||||
COORDINATE_PRECISION *
|
|
||||||
((double)m_lastDenseLongitude * thread_data->PBFprimitiveBlock.granularity() +
|
|
||||||
thread_data->PBFprimitiveBlock.lon_offset()) /
|
|
||||||
NANO);
|
|
||||||
while (denseTagIndex < dense.keys_vals_size())
|
|
||||||
{
|
|
||||||
const int tagValue = dense.keys_vals(denseTagIndex);
|
|
||||||
if (0 == tagValue)
|
|
||||||
{
|
|
||||||
++denseTagIndex;
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
const int keyValue = dense.keys_vals(denseTagIndex + 1);
|
|
||||||
const std::string &key = thread_data->PBFprimitiveBlock.stringtable().s(tagValue);
|
|
||||||
const std::string &value = thread_data->PBFprimitiveBlock.stringtable().s(keyValue);
|
|
||||||
extracted_nodes_vector[i].keyVals.Add(std::move(key), std::move(value));
|
|
||||||
denseTagIndex += 2;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
tbb::parallel_for(tbb::blocked_range<size_t>(0, extracted_nodes_vector.size()),
|
|
||||||
[this, &extracted_nodes_vector](const tbb::blocked_range<size_t> &range)
|
|
||||||
{
|
|
||||||
lua_State *lua_state = this->scripting_environment.getLuaState();
|
|
||||||
for (size_t i = range.begin(); i != range.end(); ++i)
|
|
||||||
{
|
|
||||||
ImportNode &import_node = extracted_nodes_vector[i];
|
|
||||||
ParseNodeInLua(import_node, lua_state);
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
for (const ImportNode &import_node : extracted_nodes_vector)
|
|
||||||
{
|
|
||||||
extractor_callbacks->ProcessNode(import_node);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void PBFParser::parseNode(ParserThreadData *)
|
|
||||||
{
|
|
||||||
throw OSRMException("Parsing of simple nodes not supported. PBF should use dense nodes");
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void PBFParser::parseRelation(ParserThreadData *thread_data)
|
|
||||||
{
|
|
||||||
// TODO: leave early, if relation is not a restriction
|
|
||||||
// TODO: reuse rawRestriction container
|
|
||||||
if (!use_turn_restrictions)
|
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
const OSMPBF::PrimitiveGroup &group =
|
|
||||||
thread_data->PBFprimitiveBlock.primitivegroup(thread_data->currentGroupID);
|
|
||||||
|
|
||||||
for (int i = 0, relation_size = group.relations_size(); i < relation_size; ++i)
|
|
||||||
{
|
|
||||||
std::string except_tag_string;
|
|
||||||
const OSMPBF::Relation &inputRelation =
|
|
||||||
thread_data->PBFprimitiveBlock.primitivegroup(thread_data->currentGroupID).relations(i);
|
|
||||||
bool is_restriction = false;
|
|
||||||
bool is_only_restriction = false;
|
|
||||||
for (int k = 0, endOfKeys = inputRelation.keys_size(); k < endOfKeys; ++k)
|
|
||||||
{
|
|
||||||
const std::string &key =
|
|
||||||
thread_data->PBFprimitiveBlock.stringtable().s(inputRelation.keys(k));
|
|
||||||
const std::string &val =
|
|
||||||
thread_data->PBFprimitiveBlock.stringtable().s(inputRelation.vals(k));
|
|
||||||
if ("type" == key)
|
|
||||||
{
|
|
||||||
if ("restriction" == val)
|
|
||||||
{
|
|
||||||
is_restriction = true;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (("restriction" == key) && (val.find("only_") == 0))
|
|
||||||
{
|
|
||||||
is_only_restriction = true;
|
|
||||||
}
|
|
||||||
if ("except" == key)
|
|
||||||
{
|
|
||||||
except_tag_string = val;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (is_restriction && ShouldIgnoreRestriction(except_tag_string))
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (is_restriction)
|
|
||||||
{
|
|
||||||
int64_t last_ref = 0;
|
|
||||||
InputRestrictionContainer current_restriction_container(is_only_restriction);
|
|
||||||
for (int rolesIndex = 0, last_role = inputRelation.roles_sid_size();
|
|
||||||
rolesIndex < last_role;
|
|
||||||
++rolesIndex)
|
|
||||||
{
|
|
||||||
const std::string &role = thread_data->PBFprimitiveBlock.stringtable().s(
|
|
||||||
inputRelation.roles_sid(rolesIndex));
|
|
||||||
last_ref += inputRelation.memids(rolesIndex);
|
|
||||||
|
|
||||||
if (!("from" == role || "to" == role || "via" == role))
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
switch (inputRelation.types(rolesIndex))
|
|
||||||
{
|
|
||||||
case 0: // node
|
|
||||||
if ("from" == role || "to" == role)
|
|
||||||
{ // Only via should be a node
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
BOOST_ASSERT("via" == role);
|
|
||||||
if (std::numeric_limits<unsigned>::max() !=
|
|
||||||
current_restriction_container.viaNode)
|
|
||||||
{
|
|
||||||
current_restriction_container.viaNode =
|
|
||||||
std::numeric_limits<unsigned>::max();
|
|
||||||
}
|
|
||||||
BOOST_ASSERT(std::numeric_limits<unsigned>::max() ==
|
|
||||||
current_restriction_container.viaNode);
|
|
||||||
current_restriction_container.restriction.viaNode =
|
|
||||||
static_cast<NodeID>(last_ref);
|
|
||||||
break;
|
|
||||||
case 1: // way
|
|
||||||
BOOST_ASSERT("from" == role || "to" == role || "via" == role);
|
|
||||||
if ("from" == role)
|
|
||||||
{
|
|
||||||
current_restriction_container.fromWay = static_cast<EdgeID>(last_ref);
|
|
||||||
}
|
|
||||||
if ("to" == role)
|
|
||||||
{
|
|
||||||
current_restriction_container.toWay = static_cast<EdgeID>(last_ref);
|
|
||||||
}
|
|
||||||
if ("via" == role)
|
|
||||||
{
|
|
||||||
BOOST_ASSERT(current_restriction_container.restriction.toNode ==
|
|
||||||
std::numeric_limits<unsigned>::max());
|
|
||||||
current_restriction_container.viaNode = static_cast<NodeID>(last_ref);
|
|
||||||
}
|
|
||||||
break;
|
|
||||||
case 2: // relation, not used. relations relating to relations are evil.
|
|
||||||
continue;
|
|
||||||
BOOST_ASSERT(false);
|
|
||||||
break;
|
|
||||||
|
|
||||||
default: // should not happen
|
|
||||||
BOOST_ASSERT(false);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (!extractor_callbacks->ProcessRestriction(current_restriction_container))
|
|
||||||
{
|
|
||||||
std::cerr << "[PBFParser] relation not parsed" << std::endl;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void PBFParser::parseWay(ParserThreadData *thread_data)
|
|
||||||
{
|
|
||||||
const int number_of_ways =
|
|
||||||
thread_data->PBFprimitiveBlock.primitivegroup(thread_data->currentGroupID).ways_size();
|
|
||||||
std::vector<ExtractionWay> parsed_way_vector(number_of_ways);
|
|
||||||
for (int i = 0; i < number_of_ways; ++i)
|
|
||||||
{
|
|
||||||
const OSMPBF::Way &input_way =
|
|
||||||
thread_data->PBFprimitiveBlock.primitivegroup(thread_data->currentGroupID).ways(i);
|
|
||||||
parsed_way_vector[i].id = static_cast<EdgeID>(input_way.id());
|
|
||||||
unsigned node_id_in_path = 0;
|
|
||||||
const auto number_of_referenced_nodes = input_way.refs_size();
|
|
||||||
for (auto j = 0; j < number_of_referenced_nodes; ++j)
|
|
||||||
{
|
|
||||||
node_id_in_path += static_cast<NodeID>(input_way.refs(j));
|
|
||||||
parsed_way_vector[i].path.push_back(node_id_in_path);
|
|
||||||
}
|
|
||||||
BOOST_ASSERT(input_way.keys_size() == input_way.vals_size());
|
|
||||||
const auto number_of_keys = input_way.keys_size();
|
|
||||||
for (auto j = 0; j < number_of_keys; ++j)
|
|
||||||
{
|
|
||||||
const std::string &key =
|
|
||||||
thread_data->PBFprimitiveBlock.stringtable().s(input_way.keys(j));
|
|
||||||
const std::string &val =
|
|
||||||
thread_data->PBFprimitiveBlock.stringtable().s(input_way.vals(j));
|
|
||||||
parsed_way_vector[i].keyVals.Add(std::move(key), std::move(val));
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
// TODO: investigate if schedule guided will be handled by tbb automatically
|
|
||||||
tbb::parallel_for(tbb::blocked_range<size_t>(0, parsed_way_vector.size()),
|
|
||||||
[this, &parsed_way_vector](const tbb::blocked_range<size_t> &range)
|
|
||||||
{
|
|
||||||
lua_State *lua_state = this->scripting_environment.getLuaState();
|
|
||||||
for (size_t i = range.begin(); i != range.end(); i++)
|
|
||||||
{
|
|
||||||
ExtractionWay &extraction_way = parsed_way_vector[i];
|
|
||||||
if (2 <= extraction_way.path.size())
|
|
||||||
{
|
|
||||||
ParseWayInLua(extraction_way, lua_state);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
});
|
|
||||||
|
|
||||||
for (ExtractionWay &extraction_way : parsed_way_vector)
|
|
||||||
{
|
|
||||||
if (2 <= extraction_way.path.size())
|
|
||||||
{
|
|
||||||
extractor_callbacks->ProcessWay(extraction_way);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void PBFParser::loadGroup(ParserThreadData *thread_data)
|
|
||||||
{
|
|
||||||
#ifndef NDEBUG
|
|
||||||
++group_count;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
const OSMPBF::PrimitiveGroup &group =
|
|
||||||
thread_data->PBFprimitiveBlock.primitivegroup(thread_data->currentGroupID);
|
|
||||||
thread_data->entityTypeIndicator = TypeDummy;
|
|
||||||
if (0 != group.nodes_size())
|
|
||||||
{
|
|
||||||
thread_data->entityTypeIndicator = TypeNode;
|
|
||||||
}
|
|
||||||
if (0 != group.ways_size())
|
|
||||||
{
|
|
||||||
thread_data->entityTypeIndicator = TypeWay;
|
|
||||||
}
|
|
||||||
if (0 != group.relations_size())
|
|
||||||
{
|
|
||||||
thread_data->entityTypeIndicator = TypeRelation;
|
|
||||||
}
|
|
||||||
if (group.has_dense())
|
|
||||||
{
|
|
||||||
thread_data->entityTypeIndicator = TypeDenseNode;
|
|
||||||
BOOST_ASSERT(0 != group.dense().id_size());
|
|
||||||
}
|
|
||||||
BOOST_ASSERT(thread_data->entityTypeIndicator != TypeDummy);
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void PBFParser::loadBlock(ParserThreadData *thread_data)
|
|
||||||
{
|
|
||||||
++block_count;
|
|
||||||
thread_data->currentGroupID = 0;
|
|
||||||
thread_data->currentEntityID = 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool PBFParser::readPBFBlobHeader(std::fstream &stream, ParserThreadData *thread_data)
|
|
||||||
{
|
|
||||||
int size(0);
|
|
||||||
stream.read((char *)&size, sizeof(int));
|
|
||||||
size = SwapEndian(size);
|
|
||||||
if (stream.eof())
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
if (size > MAX_BLOB_HEADER_SIZE || size < 0)
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
char *data = new char[size];
|
|
||||||
stream.read(data, size * sizeof(data[0]));
|
|
||||||
|
|
||||||
bool dataSuccessfullyParsed = (thread_data->PBFBlobHeader).ParseFromArray(data, size);
|
|
||||||
delete[] data;
|
|
||||||
return dataSuccessfullyParsed;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool PBFParser::unpackZLIB(ParserThreadData *thread_data)
|
|
||||||
{
|
|
||||||
auto raw_size = thread_data->PBFBlob.raw_size();
|
|
||||||
char *unpacked_data_array = new char[raw_size];
|
|
||||||
z_stream compressed_data_stream;
|
|
||||||
compressed_data_stream.next_in = (unsigned char *)thread_data->PBFBlob.zlib_data().data();
|
|
||||||
compressed_data_stream.avail_in = thread_data->PBFBlob.zlib_data().size();
|
|
||||||
compressed_data_stream.next_out = (unsigned char *)unpacked_data_array;
|
|
||||||
compressed_data_stream.avail_out = raw_size;
|
|
||||||
compressed_data_stream.zalloc = Z_NULL;
|
|
||||||
compressed_data_stream.zfree = Z_NULL;
|
|
||||||
compressed_data_stream.opaque = Z_NULL;
|
|
||||||
int return_code = inflateInit(&compressed_data_stream);
|
|
||||||
if (return_code != Z_OK)
|
|
||||||
{
|
|
||||||
std::cerr << "[error] failed to init zlib stream" << std::endl;
|
|
||||||
delete[] unpacked_data_array;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return_code = inflate(&compressed_data_stream, Z_FINISH);
|
|
||||||
if (return_code != Z_STREAM_END)
|
|
||||||
{
|
|
||||||
std::cerr << "[error] failed to inflate zlib stream" << std::endl;
|
|
||||||
std::cerr << "[error] Error type: " << return_code << std::endl;
|
|
||||||
delete[] unpacked_data_array;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
return_code = inflateEnd(&compressed_data_stream);
|
|
||||||
if (return_code != Z_OK)
|
|
||||||
{
|
|
||||||
std::cerr << "[error] failed to deinit zlib stream" << std::endl;
|
|
||||||
delete[] unpacked_data_array;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
thread_data->charBuffer.clear();
|
|
||||||
thread_data->charBuffer.resize(raw_size);
|
|
||||||
std::copy(unpacked_data_array, unpacked_data_array + raw_size, thread_data->charBuffer.begin());
|
|
||||||
delete[] unpacked_data_array;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
inline bool PBFParser::unpackLZMA(ParserThreadData *) { return false; }
|
|
||||||
|
|
||||||
inline bool PBFParser::readBlob(std::fstream &stream, ParserThreadData *thread_data)
|
|
||||||
{
|
|
||||||
if (stream.eof())
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
const int size = thread_data->PBFBlobHeader.datasize();
|
|
||||||
if (size < 0 || size > MAX_BLOB_SIZE)
|
|
||||||
{
|
|
||||||
std::cerr << "[error] invalid Blob size:" << size << std::endl;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
char *data = new char[size];
|
|
||||||
stream.read(data, sizeof(data[0]) * size);
|
|
||||||
|
|
||||||
if (!thread_data->PBFBlob.ParseFromArray(data, size))
|
|
||||||
{
|
|
||||||
std::cerr << "[error] failed to parse blob" << std::endl;
|
|
||||||
delete[] data;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (thread_data->PBFBlob.has_raw())
|
|
||||||
{
|
|
||||||
const std::string &data = thread_data->PBFBlob.raw();
|
|
||||||
thread_data->charBuffer.clear();
|
|
||||||
thread_data->charBuffer.resize(data.size());
|
|
||||||
std::copy(data.begin(), data.end(), thread_data->charBuffer.begin());
|
|
||||||
}
|
|
||||||
else if (thread_data->PBFBlob.has_zlib_data())
|
|
||||||
{
|
|
||||||
if (!unpackZLIB(thread_data))
|
|
||||||
{
|
|
||||||
std::cerr << "[error] zlib data encountered that could not be unpacked" << std::endl;
|
|
||||||
delete[] data;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (thread_data->PBFBlob.has_lzma_data())
|
|
||||||
{
|
|
||||||
if (!unpackLZMA(thread_data))
|
|
||||||
{
|
|
||||||
std::cerr << "[error] lzma data encountered that could not be unpacked" << std::endl;
|
|
||||||
}
|
|
||||||
delete[] data;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
std::cerr << "[error] Blob contains no data" << std::endl;
|
|
||||||
delete[] data;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
delete[] data;
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool PBFParser::readNextBlock(std::fstream &stream, ParserThreadData *thread_data)
|
|
||||||
{
|
|
||||||
if (stream.eof())
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!readPBFBlobHeader(stream, thread_data))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (thread_data->PBFBlobHeader.type() != "OSMData")
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!readBlob(stream, thread_data))
|
|
||||||
{
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!thread_data->PBFprimitiveBlock.ParseFromArray(&(thread_data->charBuffer[0]),
|
|
||||||
thread_data->charBuffer.size()))
|
|
||||||
{
|
|
||||||
std::cerr << "failed to parse PrimitiveBlock" << std::endl;
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
@@ -1,103 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef PBFPARSER_H_
|
|
||||||
#define PBFPARSER_H_
|
|
||||||
|
|
||||||
#include "BaseParser.h"
|
|
||||||
#include "../DataStructures/ConcurrentQueue.h"
|
|
||||||
|
|
||||||
#include <osmpbf/fileformat.pb.h>
|
|
||||||
#include <osmpbf/osmformat.pb.h>
|
|
||||||
|
|
||||||
#include <fstream>
|
|
||||||
#include <memory>
|
|
||||||
|
|
||||||
class PBFParser : public BaseParser
|
|
||||||
{
|
|
||||||
|
|
||||||
enum EntityType
|
|
||||||
{ TypeDummy = 0,
|
|
||||||
TypeNode = 1,
|
|
||||||
TypeWay = 2,
|
|
||||||
TypeRelation = 4,
|
|
||||||
TypeDenseNode = 8 };
|
|
||||||
|
|
||||||
struct ParserThreadData
|
|
||||||
{
|
|
||||||
int currentGroupID;
|
|
||||||
int currentEntityID;
|
|
||||||
EntityType entityTypeIndicator;
|
|
||||||
|
|
||||||
OSMPBF::BlobHeader PBFBlobHeader;
|
|
||||||
OSMPBF::Blob PBFBlob;
|
|
||||||
|
|
||||||
OSMPBF::HeaderBlock PBFHeaderBlock;
|
|
||||||
OSMPBF::PrimitiveBlock PBFprimitiveBlock;
|
|
||||||
|
|
||||||
std::vector<char> charBuffer;
|
|
||||||
};
|
|
||||||
|
|
||||||
public:
|
|
||||||
PBFParser(const char *file_name,
|
|
||||||
ExtractorCallbacks *extractor_callbacks,
|
|
||||||
ScriptingEnvironment &scripting_environment,
|
|
||||||
unsigned num_parser_threads = 0);
|
|
||||||
virtual ~PBFParser();
|
|
||||||
|
|
||||||
inline bool ReadHeader();
|
|
||||||
inline bool Parse();
|
|
||||||
|
|
||||||
private:
|
|
||||||
inline void ReadData();
|
|
||||||
inline void ParseData();
|
|
||||||
inline void parseDenseNode(ParserThreadData *thread_data);
|
|
||||||
inline void parseNode(ParserThreadData *thread_data);
|
|
||||||
inline void parseRelation(ParserThreadData *thread_data);
|
|
||||||
inline void parseWay(ParserThreadData *thread_data);
|
|
||||||
|
|
||||||
inline void loadGroup(ParserThreadData *thread_data);
|
|
||||||
inline void loadBlock(ParserThreadData *thread_data);
|
|
||||||
inline bool readPBFBlobHeader(std::fstream &stream, ParserThreadData *thread_data);
|
|
||||||
inline bool unpackZLIB(ParserThreadData *thread_data);
|
|
||||||
inline bool unpackLZMA(ParserThreadData *thread_data);
|
|
||||||
inline bool readBlob(std::fstream &stream, ParserThreadData *thread_data);
|
|
||||||
inline bool readNextBlock(std::fstream &stream, ParserThreadData *thread_data);
|
|
||||||
|
|
||||||
static const int NANO = 1000 * 1000 * 1000;
|
|
||||||
static const int MAX_BLOB_HEADER_SIZE = 64 * 1024;
|
|
||||||
static const int MAX_BLOB_SIZE = 32 * 1024 * 1024;
|
|
||||||
|
|
||||||
unsigned group_count;
|
|
||||||
unsigned block_count;
|
|
||||||
|
|
||||||
std::fstream input; // the input stream to parse
|
|
||||||
std::shared_ptr<ConcurrentQueue<ParserThreadData *>> thread_data_queue;
|
|
||||||
unsigned num_parser_threads;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif /* PBFPARSER_H_ */
|
|
||||||
@@ -1,354 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "XMLParser.h"
|
|
||||||
|
|
||||||
#include "ExtractionWay.h"
|
|
||||||
#include "ExtractorCallbacks.h"
|
|
||||||
|
|
||||||
#include "../DataStructures/HashTable.h"
|
|
||||||
#include "../DataStructures/ImportNode.h"
|
|
||||||
#include "../DataStructures/InputReaderFactory.h"
|
|
||||||
#include "../DataStructures/Restriction.h"
|
|
||||||
#include "../Util/cast.hpp"
|
|
||||||
#include "../Util/simple_logger.hpp"
|
|
||||||
#include "../Util/StringUtil.h"
|
|
||||||
#include "../typedefs.h"
|
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
|
||||||
|
|
||||||
XMLParser::XMLParser(const char *filename,
|
|
||||||
ExtractorCallbacks *extractor_callbacks,
|
|
||||||
ScriptingEnvironment &scripting_environment)
|
|
||||||
: BaseParser(extractor_callbacks, scripting_environment)
|
|
||||||
{
|
|
||||||
inputReader = inputReaderFactory(filename);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool XMLParser::ReadHeader() { return xmlTextReaderRead(inputReader) == 1; }
|
|
||||||
bool XMLParser::Parse()
|
|
||||||
{
|
|
||||||
while (xmlTextReaderRead(inputReader) == 1)
|
|
||||||
{
|
|
||||||
const int type = xmlTextReaderNodeType(inputReader);
|
|
||||||
|
|
||||||
// 1 is Element
|
|
||||||
if (type != 1)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
xmlChar *currentName = xmlTextReaderName(inputReader);
|
|
||||||
if (currentName == nullptr)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (xmlStrEqual(currentName, (const xmlChar *)"node") == 1)
|
|
||||||
{
|
|
||||||
ImportNode current_node = ReadXMLNode();
|
|
||||||
ParseNodeInLua(current_node, lua_state);
|
|
||||||
extractor_callbacks->ProcessNode(current_node);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (xmlStrEqual(currentName, (const xmlChar *)"way") == 1)
|
|
||||||
{
|
|
||||||
ExtractionWay way = ReadXMLWay();
|
|
||||||
ParseWayInLua(way, lua_state);
|
|
||||||
extractor_callbacks->ProcessWay(way);
|
|
||||||
}
|
|
||||||
if (use_turn_restrictions && xmlStrEqual(currentName, (const xmlChar *)"relation") == 1)
|
|
||||||
{
|
|
||||||
InputRestrictionContainer current_restriction = ReadXMLRestriction();
|
|
||||||
if ((UINT_MAX != current_restriction.fromWay) &&
|
|
||||||
!extractor_callbacks->ProcessRestriction(current_restriction))
|
|
||||||
{
|
|
||||||
std::cerr << "[XMLParser] restriction not parsed" << std::endl;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
xmlFree(currentName);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
InputRestrictionContainer XMLParser::ReadXMLRestriction()
|
|
||||||
{
|
|
||||||
|
|
||||||
InputRestrictionContainer restriction;
|
|
||||||
|
|
||||||
if (xmlTextReaderIsEmptyElement(inputReader) == 1)
|
|
||||||
{
|
|
||||||
return restriction;
|
|
||||||
}
|
|
||||||
|
|
||||||
std::string except_tag_string;
|
|
||||||
const int depth = xmlTextReaderDepth(inputReader);
|
|
||||||
while (xmlTextReaderRead(inputReader) == 1)
|
|
||||||
{
|
|
||||||
const int child_type = xmlTextReaderNodeType(inputReader);
|
|
||||||
if (child_type != 1 && child_type != 15)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
const int child_depth = xmlTextReaderDepth(inputReader);
|
|
||||||
xmlChar *child_name = xmlTextReaderName(inputReader);
|
|
||||||
if (child_name == nullptr)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
if (depth == child_depth && child_type == 15 &&
|
|
||||||
xmlStrEqual(child_name, (const xmlChar *)"relation") == 1)
|
|
||||||
{
|
|
||||||
xmlFree(child_name);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (child_type != 1)
|
|
||||||
{
|
|
||||||
xmlFree(child_name);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (xmlStrEqual(child_name, (const xmlChar *)"tag") == 1)
|
|
||||||
{
|
|
||||||
xmlChar *key = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"k");
|
|
||||||
xmlChar *value = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"v");
|
|
||||||
if (key != nullptr && value != nullptr)
|
|
||||||
{
|
|
||||||
if (xmlStrEqual(key, (const xmlChar *)"restriction") &&
|
|
||||||
StringStartsWith((const char *)value, "only_"))
|
|
||||||
{
|
|
||||||
restriction.restriction.flags.isOnly = true;
|
|
||||||
}
|
|
||||||
if (xmlStrEqual(key, (const xmlChar *)"except"))
|
|
||||||
{
|
|
||||||
except_tag_string = (const char *)value;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (key != nullptr)
|
|
||||||
{
|
|
||||||
xmlFree(key);
|
|
||||||
}
|
|
||||||
if (value != nullptr)
|
|
||||||
{
|
|
||||||
xmlFree(value);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (xmlStrEqual(child_name, (const xmlChar *)"member") == 1)
|
|
||||||
{
|
|
||||||
xmlChar *ref = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"ref");
|
|
||||||
if (ref != nullptr)
|
|
||||||
{
|
|
||||||
xmlChar *role = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"role");
|
|
||||||
xmlChar *type = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"type");
|
|
||||||
|
|
||||||
if (xmlStrEqual(role, (const xmlChar *)"to") &&
|
|
||||||
xmlStrEqual(type, (const xmlChar *)"way"))
|
|
||||||
{
|
|
||||||
restriction.toWay = cast::string_to_uint((const char *)ref);
|
|
||||||
}
|
|
||||||
if (xmlStrEqual(role, (const xmlChar *)"from") &&
|
|
||||||
xmlStrEqual(type, (const xmlChar *)"way"))
|
|
||||||
{
|
|
||||||
restriction.fromWay = cast::string_to_uint((const char *)ref);
|
|
||||||
}
|
|
||||||
if (xmlStrEqual(role, (const xmlChar *)"via") &&
|
|
||||||
xmlStrEqual(type, (const xmlChar *)"node"))
|
|
||||||
{
|
|
||||||
restriction.restriction.viaNode = cast::string_to_uint((const char *)ref);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (nullptr != type)
|
|
||||||
{
|
|
||||||
xmlFree(type);
|
|
||||||
}
|
|
||||||
if (nullptr != role)
|
|
||||||
{
|
|
||||||
xmlFree(role);
|
|
||||||
}
|
|
||||||
if (nullptr != ref)
|
|
||||||
{
|
|
||||||
xmlFree(ref);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
xmlFree(child_name);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (ShouldIgnoreRestriction(except_tag_string))
|
|
||||||
{
|
|
||||||
restriction.fromWay = UINT_MAX; // workaround to ignore the restriction
|
|
||||||
}
|
|
||||||
return restriction;
|
|
||||||
}
|
|
||||||
|
|
||||||
ExtractionWay XMLParser::ReadXMLWay()
|
|
||||||
{
|
|
||||||
ExtractionWay way;
|
|
||||||
if (xmlTextReaderIsEmptyElement(inputReader) == 1)
|
|
||||||
{
|
|
||||||
return way;
|
|
||||||
}
|
|
||||||
const int depth = xmlTextReaderDepth(inputReader);
|
|
||||||
while (xmlTextReaderRead(inputReader) == 1)
|
|
||||||
{
|
|
||||||
const int child_type = xmlTextReaderNodeType(inputReader);
|
|
||||||
if (child_type != 1 && child_type != 15)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
const int child_depth = xmlTextReaderDepth(inputReader);
|
|
||||||
xmlChar *child_name = xmlTextReaderName(inputReader);
|
|
||||||
if (child_name == nullptr)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (depth == child_depth && child_type == 15 &&
|
|
||||||
xmlStrEqual(child_name, (const xmlChar *)"way") == 1)
|
|
||||||
{
|
|
||||||
xmlChar *way_id = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"id");
|
|
||||||
way.id = cast::string_to_uint((char *)way_id);
|
|
||||||
xmlFree(way_id);
|
|
||||||
xmlFree(child_name);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (child_type != 1)
|
|
||||||
{
|
|
||||||
xmlFree(child_name);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (xmlStrEqual(child_name, (const xmlChar *)"tag") == 1)
|
|
||||||
{
|
|
||||||
xmlChar *key = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"k");
|
|
||||||
xmlChar *value = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"v");
|
|
||||||
|
|
||||||
if (key != nullptr && value != nullptr)
|
|
||||||
{
|
|
||||||
way.keyVals.Add(std::string((char *)key), std::string((char *)value));
|
|
||||||
}
|
|
||||||
if (key != nullptr)
|
|
||||||
{
|
|
||||||
xmlFree(key);
|
|
||||||
}
|
|
||||||
if (value != nullptr)
|
|
||||||
{
|
|
||||||
xmlFree(value);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
else if (xmlStrEqual(child_name, (const xmlChar *)"nd") == 1)
|
|
||||||
{
|
|
||||||
xmlChar *ref = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"ref");
|
|
||||||
if (ref != nullptr)
|
|
||||||
{
|
|
||||||
way.path.push_back(cast::string_to_uint((const char *)ref));
|
|
||||||
xmlFree(ref);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
xmlFree(child_name);
|
|
||||||
}
|
|
||||||
return way;
|
|
||||||
}
|
|
||||||
|
|
||||||
ImportNode XMLParser::ReadXMLNode()
|
|
||||||
{
|
|
||||||
ImportNode node;
|
|
||||||
|
|
||||||
xmlChar *attribute = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"lat");
|
|
||||||
if (attribute != nullptr)
|
|
||||||
{
|
|
||||||
node.lat = static_cast<int>(COORDINATE_PRECISION * cast::string_to_double((const char *)attribute));
|
|
||||||
xmlFree(attribute);
|
|
||||||
}
|
|
||||||
attribute = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"lon");
|
|
||||||
if (attribute != nullptr)
|
|
||||||
{
|
|
||||||
node.lon = static_cast<int>(COORDINATE_PRECISION * cast::string_to_double((const char *)attribute));
|
|
||||||
xmlFree(attribute);
|
|
||||||
}
|
|
||||||
attribute = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"id");
|
|
||||||
if (attribute != nullptr)
|
|
||||||
{
|
|
||||||
node.node_id = cast::string_to_uint((const char *)attribute);
|
|
||||||
xmlFree(attribute);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (xmlTextReaderIsEmptyElement(inputReader) == 1)
|
|
||||||
{
|
|
||||||
return node;
|
|
||||||
}
|
|
||||||
const int depth = xmlTextReaderDepth(inputReader);
|
|
||||||
while (xmlTextReaderRead(inputReader) == 1)
|
|
||||||
{
|
|
||||||
const int child_type = xmlTextReaderNodeType(inputReader);
|
|
||||||
// 1 = Element, 15 = EndElement
|
|
||||||
if (child_type != 1 && child_type != 15)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
const int child_depth = xmlTextReaderDepth(inputReader);
|
|
||||||
xmlChar *child_name = xmlTextReaderName(inputReader);
|
|
||||||
if (child_name == nullptr)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (depth == child_depth && child_type == 15 &&
|
|
||||||
xmlStrEqual(child_name, (const xmlChar *)"node") == 1)
|
|
||||||
{
|
|
||||||
xmlFree(child_name);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
if (child_type != 1)
|
|
||||||
{
|
|
||||||
xmlFree(child_name);
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (xmlStrEqual(child_name, (const xmlChar *)"tag") == 1)
|
|
||||||
{
|
|
||||||
xmlChar *key = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"k");
|
|
||||||
xmlChar *value = xmlTextReaderGetAttribute(inputReader, (const xmlChar *)"v");
|
|
||||||
if (key != nullptr && value != nullptr)
|
|
||||||
{
|
|
||||||
node.keyVals.Add(std::string((char *)(key)), std::string((char *)(value)));
|
|
||||||
}
|
|
||||||
if (key != nullptr)
|
|
||||||
{
|
|
||||||
xmlFree(key);
|
|
||||||
}
|
|
||||||
if (value != nullptr)
|
|
||||||
{
|
|
||||||
xmlFree(value);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
xmlFree(child_name);
|
|
||||||
}
|
|
||||||
return node;
|
|
||||||
}
|
|
||||||
@@ -1,54 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef XMLPARSER_H_
|
|
||||||
#define XMLPARSER_H_
|
|
||||||
|
|
||||||
#include "BaseParser.h"
|
|
||||||
#include "../DataStructures/Restriction.h"
|
|
||||||
|
|
||||||
#include <libxml/xmlreader.h>
|
|
||||||
|
|
||||||
class ExtractorCallbacks;
|
|
||||||
|
|
||||||
class XMLParser : public BaseParser
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
XMLParser(const char *filename,
|
|
||||||
ExtractorCallbacks *extractor_callbacks,
|
|
||||||
ScriptingEnvironment &scripting_environment);
|
|
||||||
bool ReadHeader();
|
|
||||||
bool Parse();
|
|
||||||
|
|
||||||
private:
|
|
||||||
InputRestrictionContainer ReadXMLRestriction();
|
|
||||||
ExtractionWay ReadXMLWay();
|
|
||||||
ImportNode ReadXMLNode();
|
|
||||||
xmlTextReaderPtr inputReader;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif /* XMLPARSER_H_ */
|
|
||||||
@@ -32,8 +32,10 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
#include <string>
|
#include <string>
|
||||||
#include <type_traits>
|
#include <type_traits>
|
||||||
|
|
||||||
|
namespace
|
||||||
|
{
|
||||||
constexpr float COORDINATE_PRECISION = 1000000.f;
|
constexpr float COORDINATE_PRECISION = 1000000.f;
|
||||||
|
}
|
||||||
struct FixedPointCoordinate
|
struct FixedPointCoordinate
|
||||||
{
|
{
|
||||||
int lat;
|
int lat;
|
||||||
@@ -51,7 +53,7 @@ struct FixedPointCoordinate
|
|||||||
|
|
||||||
void Reset();
|
void Reset();
|
||||||
bool isSet() const;
|
bool isSet() const;
|
||||||
bool isValid() const;
|
bool is_valid() const;
|
||||||
bool operator==(const FixedPointCoordinate &other) const;
|
bool operator==(const FixedPointCoordinate &other) const;
|
||||||
|
|
||||||
static double
|
static double
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -34,13 +34,12 @@ namespace boost { namespace interprocess { class named_mutex; } }
|
|||||||
#include <osrm/RouteParameters.h>
|
#include <osrm/RouteParameters.h>
|
||||||
#include <osrm/ServerPaths.h>
|
#include <osrm/ServerPaths.h>
|
||||||
|
|
||||||
#include "../Plugins/BasePlugin.h"
|
#include "../plugins/distance_table.hpp"
|
||||||
#include "../Plugins/DistanceTablePlugin.h"
|
#include "../plugins/hello_world.hpp"
|
||||||
#include "../Plugins/HelloWorldPlugin.h"
|
#include "../plugins/locate.hpp"
|
||||||
#include "../Plugins/LocatePlugin.h"
|
#include "../plugins/nearest.hpp"
|
||||||
#include "../Plugins/NearestPlugin.h"
|
#include "../plugins/timestamp.hpp"
|
||||||
#include "../Plugins/TimestampPlugin.h"
|
#include "../plugins/viaroute.hpp"
|
||||||
#include "../Plugins/ViaRoutePlugin.h"
|
|
||||||
#include "../Server/DataStructures/BaseDataFacade.h"
|
#include "../Server/DataStructures/BaseDataFacade.h"
|
||||||
#include "../Server/DataStructures/InternalDataFacade.h"
|
#include "../Server/DataStructures/InternalDataFacade.h"
|
||||||
#include "../Server/DataStructures/SharedBarriers.h"
|
#include "../Server/DataStructures/SharedBarriers.h"
|
||||||
|
|||||||
+1
-1
@@ -34,7 +34,7 @@ struct RouteParameters;
|
|||||||
|
|
||||||
#include <osrm/ServerPaths.h>
|
#include <osrm/ServerPaths.h>
|
||||||
|
|
||||||
#include "../DataStructures/QueryEdge.h"
|
#include "../data_structures/query_edge.hpp"
|
||||||
|
|
||||||
#include <memory>
|
#include <memory>
|
||||||
#include <unordered_map>
|
#include <unordered_map>
|
||||||
|
|||||||
@@ -1,176 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef VIA_ROUTE_PLUGIN_H
|
|
||||||
#define VIA_ROUTE_PLUGIN_H
|
|
||||||
|
|
||||||
#include "BasePlugin.h"
|
|
||||||
|
|
||||||
#include "../Algorithms/ObjectToBase64.h"
|
|
||||||
#include "../DataStructures/QueryEdge.h"
|
|
||||||
#include "../DataStructures/SearchEngine.h"
|
|
||||||
#include "../Descriptors/BaseDescriptor.h"
|
|
||||||
#include "../Descriptors/GPXDescriptor.h"
|
|
||||||
#include "../Descriptors/JSONDescriptor.h"
|
|
||||||
#include "../Util/make_unique.hpp"
|
|
||||||
#include "../Util/simple_logger.hpp"
|
|
||||||
#include "../Util/StringUtil.h"
|
|
||||||
#include "../Util/TimingUtil.h"
|
|
||||||
|
|
||||||
#include <cstdlib>
|
|
||||||
|
|
||||||
#include <algorithm>
|
|
||||||
#include <memory>
|
|
||||||
#include <unordered_map>
|
|
||||||
#include <string>
|
|
||||||
#include <vector>
|
|
||||||
|
|
||||||
template <class DataFacadeT> class ViaRoutePlugin final : public BasePlugin
|
|
||||||
{
|
|
||||||
private:
|
|
||||||
std::unordered_map<std::string, unsigned> descriptor_table;
|
|
||||||
std::unique_ptr<SearchEngine<DataFacadeT>> search_engine_ptr;
|
|
||||||
|
|
||||||
public:
|
|
||||||
explicit ViaRoutePlugin(DataFacadeT *facade) : descriptor_string("viaroute"), facade(facade)
|
|
||||||
{
|
|
||||||
search_engine_ptr = osrm::make_unique<SearchEngine<DataFacadeT>>(facade);
|
|
||||||
|
|
||||||
descriptor_table.emplace("json", 0);
|
|
||||||
descriptor_table.emplace("gpx", 1);
|
|
||||||
// descriptor_table.emplace("geojson", 2);
|
|
||||||
}
|
|
||||||
|
|
||||||
virtual ~ViaRoutePlugin() {}
|
|
||||||
|
|
||||||
const std::string GetDescriptor() const final { return descriptor_string; }
|
|
||||||
|
|
||||||
void HandleRequest(const RouteParameters &route_parameters, http::Reply &reply) final
|
|
||||||
{
|
|
||||||
// check number of parameters
|
|
||||||
if (2 > route_parameters.coordinates.size() ||
|
|
||||||
std::any_of(begin(route_parameters.coordinates),
|
|
||||||
end(route_parameters.coordinates),
|
|
||||||
[&](FixedPointCoordinate coordinate)
|
|
||||||
{
|
|
||||||
return !coordinate.isValid();
|
|
||||||
}))
|
|
||||||
{
|
|
||||||
reply = http::Reply::StockReply(http::Reply::badRequest);
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
RawRouteData raw_route;
|
|
||||||
raw_route.check_sum = facade->GetCheckSum();
|
|
||||||
for (const FixedPointCoordinate &coordinate : route_parameters.coordinates)
|
|
||||||
{
|
|
||||||
raw_route.raw_via_node_coordinates.emplace_back(coordinate);
|
|
||||||
}
|
|
||||||
|
|
||||||
std::vector<PhantomNode> phantom_node_vector(raw_route.raw_via_node_coordinates.size());
|
|
||||||
const bool checksum_OK = (route_parameters.check_sum == raw_route.check_sum);
|
|
||||||
|
|
||||||
for (unsigned i = 0; i < raw_route.raw_via_node_coordinates.size(); ++i)
|
|
||||||
{
|
|
||||||
if (checksum_OK && i < route_parameters.hints.size() &&
|
|
||||||
!route_parameters.hints[i].empty())
|
|
||||||
{
|
|
||||||
ObjectEncoder::DecodeFromBase64(route_parameters.hints[i], phantom_node_vector[i]);
|
|
||||||
if (phantom_node_vector[i].isValid(facade->GetNumberOfNodes()))
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
facade->FindPhantomNodeForCoordinate(raw_route.raw_via_node_coordinates[i],
|
|
||||||
phantom_node_vector[i],
|
|
||||||
route_parameters.zoom_level);
|
|
||||||
}
|
|
||||||
|
|
||||||
PhantomNodes current_phantom_node_pair;
|
|
||||||
for (unsigned i = 0; i < phantom_node_vector.size() - 1; ++i)
|
|
||||||
{
|
|
||||||
current_phantom_node_pair.source_phantom = phantom_node_vector[i];
|
|
||||||
current_phantom_node_pair.target_phantom = phantom_node_vector[i + 1];
|
|
||||||
raw_route.segment_end_coordinates.emplace_back(current_phantom_node_pair);
|
|
||||||
}
|
|
||||||
|
|
||||||
const bool is_alternate_requested = route_parameters.alternate_route;
|
|
||||||
const bool is_only_one_segment = (1 == raw_route.segment_end_coordinates.size());
|
|
||||||
if (is_alternate_requested && is_only_one_segment)
|
|
||||||
{
|
|
||||||
search_engine_ptr->alternative_path(raw_route.segment_end_coordinates.front(),
|
|
||||||
raw_route);
|
|
||||||
}
|
|
||||||
else
|
|
||||||
{
|
|
||||||
search_engine_ptr->shortest_path(
|
|
||||||
raw_route.segment_end_coordinates, route_parameters.uturns, raw_route);
|
|
||||||
}
|
|
||||||
|
|
||||||
if (INVALID_EDGE_WEIGHT == raw_route.shortest_path_length)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logDEBUG) << "Error occurred, single path not found";
|
|
||||||
}
|
|
||||||
reply.status = http::Reply::ok;
|
|
||||||
|
|
||||||
DescriptorConfig descriptor_config;
|
|
||||||
|
|
||||||
auto iter = descriptor_table.find(route_parameters.output_format);
|
|
||||||
unsigned descriptor_type = (iter != descriptor_table.end() ? iter->second : 0);
|
|
||||||
|
|
||||||
descriptor_config.zoom_level = route_parameters.zoom_level;
|
|
||||||
descriptor_config.instructions = route_parameters.print_instructions;
|
|
||||||
descriptor_config.geometry = route_parameters.geometry;
|
|
||||||
descriptor_config.encode_geometry = route_parameters.compression;
|
|
||||||
|
|
||||||
std::shared_ptr<BaseDescriptor<DataFacadeT>> descriptor;
|
|
||||||
switch (descriptor_type)
|
|
||||||
{
|
|
||||||
// case 0:
|
|
||||||
// descriptor = std::make_shared<JSONDescriptor<DataFacadeT>>();
|
|
||||||
// break;
|
|
||||||
case 1:
|
|
||||||
descriptor = std::make_shared<GPXDescriptor<DataFacadeT>>(facade);
|
|
||||||
break;
|
|
||||||
// case 2:
|
|
||||||
// descriptor = std::make_shared<GEOJSONDescriptor<DataFacadeT>>();
|
|
||||||
// break;
|
|
||||||
default:
|
|
||||||
descriptor = std::make_shared<JSONDescriptor<DataFacadeT>>(facade);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
descriptor->SetConfig(descriptor_config);
|
|
||||||
descriptor->Run(raw_route, reply);
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
|
||||||
std::string descriptor_string;
|
|
||||||
DataFacadeT *facade;
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // VIA_ROUTE_PLUGIN_H
|
|
||||||
@@ -69,10 +69,10 @@ void Connection::handle_read(const boost::system::error_code &error, std::size_t
|
|||||||
CompressionType compression_type(noCompression);
|
CompressionType compression_type(noCompression);
|
||||||
boost::tribool result;
|
boost::tribool result;
|
||||||
boost::tie(result, boost::tuples::ignore) =
|
boost::tie(result, boost::tuples::ignore) =
|
||||||
request_parser.Parse(request,
|
RequestParser().Parse(request,
|
||||||
incoming_data_buffer.data(),
|
incoming_data_buffer.data(),
|
||||||
incoming_data_buffer.data() + bytes_transferred,
|
incoming_data_buffer.data() + bytes_transferred,
|
||||||
&compression_type);
|
compression_type);
|
||||||
|
|
||||||
// the request has been parsed
|
// the request has been parsed
|
||||||
if (result)
|
if (result)
|
||||||
|
|||||||
+1
-3
@@ -28,7 +28,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
#ifndef CONNECTION_H
|
#ifndef CONNECTION_H
|
||||||
#define CONNECTION_H
|
#define CONNECTION_H
|
||||||
|
|
||||||
#include "RequestParser.h"
|
// #include "RequestParser.h"
|
||||||
#include "Http/CompressionType.h"
|
#include "Http/CompressionType.h"
|
||||||
#include "Http/Request.h"
|
#include "Http/Request.h"
|
||||||
|
|
||||||
@@ -40,7 +40,6 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
#include <boost/version.hpp>
|
#include <boost/version.hpp>
|
||||||
|
|
||||||
#include <memory>
|
#include <memory>
|
||||||
#include <string>
|
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
//workaround for incomplete std::shared_ptr compatibility in old boost versions
|
//workaround for incomplete std::shared_ptr compatibility in old boost versions
|
||||||
@@ -97,7 +96,6 @@ class Connection : public std::enable_shared_from_this<Connection>
|
|||||||
RequestHandler &request_handler;
|
RequestHandler &request_handler;
|
||||||
boost::array<char, 8192> incoming_data_buffer;
|
boost::array<char, 8192> incoming_data_buffer;
|
||||||
Request request;
|
Request request;
|
||||||
RequestParser request_parser;
|
|
||||||
Reply reply;
|
Reply reply;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -30,11 +30,11 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
// Exposes all data access interfaces to the algorithms via base class ptr
|
// Exposes all data access interfaces to the algorithms via base class ptr
|
||||||
|
|
||||||
#include "../../DataStructures/EdgeBasedNode.h"
|
#include "../../data_structures/edge_based_node.hpp"
|
||||||
#include "../../DataStructures/ImportNode.h"
|
#include "../../data_structures/external_memory_node.hpp"
|
||||||
#include "../../DataStructures/PhantomNodes.h"
|
#include "../../data_structures/phantom_node.hpp"
|
||||||
#include "../../DataStructures/Range.h"
|
#include "../../data_structures/turn_instructions.hpp"
|
||||||
#include "../../DataStructures/TurnInstructions.h"
|
#include "../../Util/integer_range.hpp"
|
||||||
#include "../../Util/OSRMException.h"
|
#include "../../Util/OSRMException.h"
|
||||||
#include "../../Util/StringUtil.h"
|
#include "../../Util/StringUtil.h"
|
||||||
#include "../../typedefs.h"
|
#include "../../typedefs.h"
|
||||||
@@ -108,6 +108,11 @@ template <class EdgeDataT> class BaseDataFacade
|
|||||||
const unsigned zoom_level,
|
const unsigned zoom_level,
|
||||||
const unsigned number_of_results) = 0;
|
const unsigned number_of_results) = 0;
|
||||||
|
|
||||||
|
virtual bool
|
||||||
|
IncrementalFindPhantomNodeForCoordinate(const FixedPointCoordinate &input_coordinate,
|
||||||
|
PhantomNode &resulting_phantom_node,
|
||||||
|
const unsigned zoom_leve) = 0;
|
||||||
|
|
||||||
virtual unsigned GetCheckSum() const = 0;
|
virtual unsigned GetCheckSum() const = 0;
|
||||||
|
|
||||||
virtual unsigned GetNameIndexFromEdgeID(const unsigned id) const = 0;
|
virtual unsigned GetNameIndexFromEdgeID(const unsigned id) const = 0;
|
||||||
|
|||||||
@@ -32,19 +32,19 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
#include "BaseDataFacade.h"
|
#include "BaseDataFacade.h"
|
||||||
|
|
||||||
#include "../../DataStructures/OriginalEdgeData.h"
|
#include "../../data_structures/original_edge_data.hpp"
|
||||||
#include "../../DataStructures/QueryNode.h"
|
#include "../../data_structures/query_node.hpp"
|
||||||
#include "../../DataStructures/QueryEdge.h"
|
#include "../../data_structures/query_edge.hpp"
|
||||||
#include "../../DataStructures/SharedMemoryVectorWrapper.h"
|
#include "../../data_structures/shared_memory_vector_wrapper.hpp"
|
||||||
#include "../../DataStructures/StaticGraph.h"
|
#include "../../data_structures/static_graph.hpp"
|
||||||
#include "../../DataStructures/StaticRTree.h"
|
#include "../../data_structures/static_rtree.hpp"
|
||||||
#include "../../DataStructures/RangeTable.h"
|
#include "../../data_structures/range_table.hpp"
|
||||||
#include "../../Util/BoostFileSystemFix.h"
|
#include "../../Util/BoostFileSystemFix.h"
|
||||||
#include "../../Util/GraphLoader.h"
|
#include "../../Util/graph_loader.hpp"
|
||||||
#include "../../Util/ProgramOptions.h"
|
|
||||||
#include "../../Util/simple_logger.hpp"
|
#include "../../Util/simple_logger.hpp"
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
#include <osrm/Coordinate.h>
|
||||||
|
#include <osrm/ServerPaths.h>
|
||||||
|
|
||||||
template <class EdgeDataT> class InternalDataFacade : public BaseDataFacade<EdgeDataT>
|
template <class EdgeDataT> class InternalDataFacade : public BaseDataFacade<EdgeDataT>
|
||||||
{
|
{
|
||||||
@@ -126,14 +126,14 @@ template <class EdgeDataT> class InternalDataFacade : public BaseDataFacade<Edge
|
|||||||
{
|
{
|
||||||
boost::filesystem::ifstream nodes_input_stream(nodes_file, std::ios::binary);
|
boost::filesystem::ifstream nodes_input_stream(nodes_file, std::ios::binary);
|
||||||
|
|
||||||
NodeInfo current_node;
|
QueryNode current_node;
|
||||||
unsigned number_of_coordinates = 0;
|
unsigned number_of_coordinates = 0;
|
||||||
nodes_input_stream.read((char *)&number_of_coordinates, sizeof(unsigned));
|
nodes_input_stream.read((char *)&number_of_coordinates, sizeof(unsigned));
|
||||||
m_coordinate_list =
|
m_coordinate_list =
|
||||||
std::make_shared<std::vector<FixedPointCoordinate>>(number_of_coordinates);
|
std::make_shared<std::vector<FixedPointCoordinate>>(number_of_coordinates);
|
||||||
for (unsigned i = 0; i < number_of_coordinates; ++i)
|
for (unsigned i = 0; i < number_of_coordinates; ++i)
|
||||||
{
|
{
|
||||||
nodes_input_stream.read((char *)¤t_node, sizeof(NodeInfo));
|
nodes_input_stream.read((char *)¤t_node, sizeof(QueryNode));
|
||||||
m_coordinate_list->at(i) = FixedPointCoordinate(current_node.lat, current_node.lon);
|
m_coordinate_list->at(i) = FixedPointCoordinate(current_node.lat, current_node.lon);
|
||||||
BOOST_ASSERT((std::abs(m_coordinate_list->at(i).lat) >> 30) == 0);
|
BOOST_ASSERT((std::abs(m_coordinate_list->at(i).lat) >> 30) == 0);
|
||||||
BOOST_ASSERT((std::abs(m_coordinate_list->at(i).lon) >> 30) == 0);
|
BOOST_ASSERT((std::abs(m_coordinate_list->at(i).lon) >> 30) == 0);
|
||||||
@@ -390,6 +390,24 @@ template <class EdgeDataT> class InternalDataFacade : public BaseDataFacade<Edge
|
|||||||
input_coordinate, resulting_phantom_node, zoom_level);
|
input_coordinate, resulting_phantom_node, zoom_level);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
IncrementalFindPhantomNodeForCoordinate(const FixedPointCoordinate &input_coordinate,
|
||||||
|
PhantomNode &resulting_phantom_node,
|
||||||
|
const unsigned zoom_level) final
|
||||||
|
{
|
||||||
|
std::vector<PhantomNode> resulting_phantom_node_vector;
|
||||||
|
auto result = IncrementalFindPhantomNodeForCoordinate(input_coordinate,
|
||||||
|
resulting_phantom_node_vector,
|
||||||
|
zoom_level,
|
||||||
|
1);
|
||||||
|
if (result)
|
||||||
|
{
|
||||||
|
BOOST_ASSERT(!resulting_phantom_node_vector.empty());
|
||||||
|
resulting_phantom_node = resulting_phantom_node_vector.front();
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
IncrementalFindPhantomNodeForCoordinate(const FixedPointCoordinate &input_coordinate,
|
IncrementalFindPhantomNodeForCoordinate(const FixedPointCoordinate &input_coordinate,
|
||||||
std::vector<PhantomNode> &resulting_phantom_node_vector,
|
std::vector<PhantomNode> &resulting_phantom_node_vector,
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -33,11 +33,10 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
#include "BaseDataFacade.h"
|
#include "BaseDataFacade.h"
|
||||||
#include "SharedDataType.h"
|
#include "SharedDataType.h"
|
||||||
|
|
||||||
#include "../../DataStructures/RangeTable.h"
|
#include "../../data_structures/range_table.hpp"
|
||||||
#include "../../DataStructures/StaticGraph.h"
|
#include "../../data_structures/static_graph.hpp"
|
||||||
#include "../../DataStructures/StaticRTree.h"
|
#include "../../data_structures/static_rtree.hpp"
|
||||||
#include "../../Util/BoostFileSystemFix.h"
|
#include "../../Util/BoostFileSystemFix.h"
|
||||||
#include "../../Util/ProgramOptions.h"
|
|
||||||
#include "../../Util/make_unique.hpp"
|
#include "../../Util/make_unique.hpp"
|
||||||
#include "../../Util/simple_logger.hpp"
|
#include "../../Util/simple_logger.hpp"
|
||||||
|
|
||||||
@@ -276,7 +275,7 @@ template <class EdgeDataT> class SharedDataFacade : public BaseDataFacade<EdgeDa
|
|||||||
SimpleLogger().Write() << "number of geometries: " << m_coordinate_list->size();
|
SimpleLogger().Write() << "number of geometries: " << m_coordinate_list->size();
|
||||||
for (unsigned i = 0; i < m_coordinate_list->size(); ++i)
|
for (unsigned i = 0; i < m_coordinate_list->size(); ++i)
|
||||||
{
|
{
|
||||||
if (!GetCoordinateOfNode(i).isValid())
|
if (!GetCoordinateOfNode(i).is_valid())
|
||||||
{
|
{
|
||||||
SimpleLogger().Write() << "coordinate " << i << " not valid";
|
SimpleLogger().Write() << "coordinate " << i << " not valid";
|
||||||
}
|
}
|
||||||
@@ -383,6 +382,24 @@ template <class EdgeDataT> class SharedDataFacade : public BaseDataFacade<EdgeDa
|
|||||||
input_coordinate, resulting_phantom_node, zoom_level);
|
input_coordinate, resulting_phantom_node, zoom_level);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
bool
|
||||||
|
IncrementalFindPhantomNodeForCoordinate(const FixedPointCoordinate &input_coordinate,
|
||||||
|
PhantomNode &resulting_phantom_node,
|
||||||
|
const unsigned zoom_level) final
|
||||||
|
{
|
||||||
|
std::vector<PhantomNode> resulting_phantom_node_vector;
|
||||||
|
auto result = IncrementalFindPhantomNodeForCoordinate(input_coordinate,
|
||||||
|
resulting_phantom_node_vector,
|
||||||
|
zoom_level,
|
||||||
|
1);
|
||||||
|
if (result)
|
||||||
|
{
|
||||||
|
BOOST_ASSERT(!resulting_phantom_node_vector.empty());
|
||||||
|
resulting_phantom_node = resulting_phantom_node_vector.front();
|
||||||
|
}
|
||||||
|
return result;
|
||||||
|
}
|
||||||
|
|
||||||
bool
|
bool
|
||||||
IncrementalFindPhantomNodeForCoordinate(const FixedPointCoordinate &input_coordinate,
|
IncrementalFindPhantomNodeForCoordinate(const FixedPointCoordinate &input_coordinate,
|
||||||
std::vector<PhantomNode> &resulting_phantom_node_vector,
|
std::vector<PhantomNode> &resulting_phantom_node_vector,
|
||||||
|
|||||||
@@ -36,6 +36,6 @@ enum CompressionType
|
|||||||
gzipRFC1952,
|
gzipRFC1952,
|
||||||
deflateRFC1951 };
|
deflateRFC1951 };
|
||||||
|
|
||||||
} // namespace http
|
}
|
||||||
|
|
||||||
#endif // COMPRESSION_TYPE_H
|
#endif // COMPRESSION_TYPE_H
|
||||||
|
|||||||
@@ -30,8 +30,9 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
#include "APIGrammar.h"
|
#include "APIGrammar.h"
|
||||||
#include "Http/Request.h"
|
#include "Http/Request.h"
|
||||||
|
|
||||||
#include "../DataStructures/JSONContainer.h"
|
#include "../data_structures/json_container.hpp"
|
||||||
#include "../Library/OSRM.h"
|
#include "../Library/OSRM.h"
|
||||||
|
#include "../Util/json_renderer.hpp"
|
||||||
#include "../Util/simple_logger.hpp"
|
#include "../Util/simple_logger.hpp"
|
||||||
#include "../Util/StringUtil.h"
|
#include "../Util/StringUtil.h"
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|||||||
@@ -37,7 +37,7 @@ RequestParser::RequestParser() : state_(method_start), header({"", ""}) {}
|
|||||||
void RequestParser::Reset() { state_ = method_start; }
|
void RequestParser::Reset() { state_ = method_start; }
|
||||||
|
|
||||||
boost::tuple<boost::tribool, char *>
|
boost::tuple<boost::tribool, char *>
|
||||||
RequestParser::Parse(Request &req, char *begin, char *end, http::CompressionType *compression_type)
|
RequestParser::Parse(Request &req, char *begin, char *end, http::CompressionType &compression_type)
|
||||||
{
|
{
|
||||||
while (begin != end)
|
while (begin != end)
|
||||||
{
|
{
|
||||||
@@ -52,7 +52,7 @@ RequestParser::Parse(Request &req, char *begin, char *end, http::CompressionType
|
|||||||
}
|
}
|
||||||
|
|
||||||
boost::tribool
|
boost::tribool
|
||||||
RequestParser::consume(Request &req, char input, http::CompressionType *compression_type)
|
RequestParser::consume(Request &req, char input, http::CompressionType &compression_type)
|
||||||
{
|
{
|
||||||
switch (state_)
|
switch (state_)
|
||||||
{
|
{
|
||||||
@@ -178,11 +178,11 @@ RequestParser::consume(Request &req, char input, http::CompressionType *compress
|
|||||||
/* giving gzip precedence over deflate */
|
/* giving gzip precedence over deflate */
|
||||||
if (header.value.find("deflate") != std::string::npos)
|
if (header.value.find("deflate") != std::string::npos)
|
||||||
{
|
{
|
||||||
*compression_type = deflateRFC1951;
|
compression_type = deflateRFC1951;
|
||||||
}
|
}
|
||||||
if (header.value.find("gzip") != std::string::npos)
|
if (header.value.find("gzip") != std::string::npos)
|
||||||
{
|
{
|
||||||
*compression_type = gzipRFC1952;
|
compression_type = gzipRFC1952;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -46,10 +46,10 @@ class RequestParser
|
|||||||
void Reset();
|
void Reset();
|
||||||
|
|
||||||
boost::tuple<boost::tribool, char *>
|
boost::tuple<boost::tribool, char *>
|
||||||
Parse(Request &req, char *begin, char *end, CompressionType *compressionType);
|
Parse(Request &req, char *begin, char *end, CompressionType &compression_type);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
boost::tribool consume(Request &req, char input, CompressionType *compressionType);
|
boost::tribool consume(Request &req, char input, CompressionType &compression_type);
|
||||||
|
|
||||||
inline bool isChar(int c);
|
inline bool isChar(int c);
|
||||||
|
|
||||||
|
|||||||
@@ -1,130 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#include "../typedefs.h"
|
|
||||||
#include "../Algorithms/StronglyConnectedComponents.h"
|
|
||||||
#include "../Util/GraphLoader.h"
|
|
||||||
#include "../Util/OSRMException.h"
|
|
||||||
#include "../Util/simple_logger.hpp"
|
|
||||||
#include "../Util/FingerPrint.h"
|
|
||||||
|
|
||||||
#include <fstream>
|
|
||||||
#include <memory>
|
|
||||||
#include <string>
|
|
||||||
#include <vector>
|
|
||||||
|
|
||||||
std::vector<NodeInfo> coordinate_list;
|
|
||||||
std::vector<TurnRestriction> restrictions_vector;
|
|
||||||
std::vector<NodeID> bollard_ID_list;
|
|
||||||
std::vector<NodeID> trafficlight_ID_list;
|
|
||||||
|
|
||||||
int main(int argc, char *argv[])
|
|
||||||
{
|
|
||||||
LogPolicy::GetInstance().Unmute();
|
|
||||||
try
|
|
||||||
{
|
|
||||||
// enable logging
|
|
||||||
if (argc < 3)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << "usage:\n" << argv[0]
|
|
||||||
<< " <osrm> <osrm.restrictions>";
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
SimpleLogger().Write() << "Using restrictions from file: " << argv[2];
|
|
||||||
std::ifstream restriction_ifstream(argv[2], std::ios::binary);
|
|
||||||
const FingerPrint fingerprint_orig;
|
|
||||||
FingerPrint fingerprint_loaded;
|
|
||||||
restriction_ifstream.read((char *)&fingerprint_loaded, sizeof(FingerPrint));
|
|
||||||
|
|
||||||
// check fingerprint and warn if necessary
|
|
||||||
if (!fingerprint_loaded.TestGraphUtil(fingerprint_orig))
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << argv[2] << " was prepared with a different build. "
|
|
||||||
"Reprocess to get rid of this warning.";
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!restriction_ifstream.good())
|
|
||||||
{
|
|
||||||
throw OSRMException("Could not access <osrm-restrictions> files");
|
|
||||||
}
|
|
||||||
uint32_t usable_restrictions = 0;
|
|
||||||
restriction_ifstream.read((char *)&usable_restrictions, sizeof(uint32_t));
|
|
||||||
restrictions_vector.resize(usable_restrictions);
|
|
||||||
|
|
||||||
// load restrictions
|
|
||||||
if (usable_restrictions > 0)
|
|
||||||
{
|
|
||||||
restriction_ifstream.read((char *)&(restrictions_vector[0]),
|
|
||||||
usable_restrictions * sizeof(TurnRestriction));
|
|
||||||
}
|
|
||||||
restriction_ifstream.close();
|
|
||||||
|
|
||||||
std::ifstream input_stream(argv[1], std::ifstream::in | std::ifstream::binary);
|
|
||||||
if (!input_stream.is_open())
|
|
||||||
{
|
|
||||||
throw OSRMException("Cannot open osrm file");
|
|
||||||
}
|
|
||||||
|
|
||||||
// load graph data
|
|
||||||
std::vector<ImportEdge> edge_list;
|
|
||||||
const NodeID number_of_nodes = readBinaryOSRMGraphFromStream(input_stream,
|
|
||||||
edge_list,
|
|
||||||
bollard_ID_list,
|
|
||||||
trafficlight_ID_list,
|
|
||||||
&coordinate_list,
|
|
||||||
restrictions_vector);
|
|
||||||
input_stream.close();
|
|
||||||
|
|
||||||
BOOST_ASSERT_MSG(restrictions_vector.size() == usable_restrictions,
|
|
||||||
"size of restrictions_vector changed");
|
|
||||||
|
|
||||||
SimpleLogger().Write() << restrictions_vector.size() << " restrictions, "
|
|
||||||
<< bollard_ID_list.size() << " bollard nodes, "
|
|
||||||
<< trafficlight_ID_list.size() << " traffic lights";
|
|
||||||
|
|
||||||
// Building an edge-expanded graph from node-based input an turn
|
|
||||||
// restrictions
|
|
||||||
SimpleLogger().Write() << "Starting SCC graph traversal";
|
|
||||||
std::shared_ptr<TarjanSCC> tarjan = std::make_shared<TarjanSCC>(number_of_nodes,
|
|
||||||
edge_list,
|
|
||||||
bollard_ID_list,
|
|
||||||
trafficlight_ID_list,
|
|
||||||
restrictions_vector,
|
|
||||||
coordinate_list);
|
|
||||||
edge_list.clear();
|
|
||||||
edge_list.shrink_to_fit();
|
|
||||||
|
|
||||||
tarjan->Run();
|
|
||||||
SimpleLogger().Write() << "finished component analysis";
|
|
||||||
}
|
|
||||||
catch (const std::exception &e)
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << "[exception] " << e.what();
|
|
||||||
}
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
@@ -0,0 +1,109 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "../../algorithms/douglas_peucker.hpp"
|
||||||
|
#include "../../data_structures/segment_information.hpp"
|
||||||
|
#include "../../Include/osrm/Coordinate.h"
|
||||||
|
|
||||||
|
#include <boost/test/unit_test.hpp>
|
||||||
|
#include <boost/test/test_case_template.hpp>
|
||||||
|
#include <boost/mpl/list.hpp>
|
||||||
|
|
||||||
|
#include <iostream>
|
||||||
|
|
||||||
|
BOOST_AUTO_TEST_SUITE(douglas_peucker)
|
||||||
|
|
||||||
|
SegmentInformation getTestInfo(int lat, int lon, bool necessary)
|
||||||
|
{
|
||||||
|
return SegmentInformation(FixedPointCoordinate(lat, lon),
|
||||||
|
0, 0, 0, TurnInstruction::HeadOn, necessary, false, 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
BOOST_AUTO_TEST_CASE(all_necessary_test)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* x
|
||||||
|
* / \
|
||||||
|
* x \
|
||||||
|
* / \
|
||||||
|
* x x
|
||||||
|
*/
|
||||||
|
std::vector<SegmentInformation> info = {
|
||||||
|
getTestInfo(5, 5, true),
|
||||||
|
getTestInfo(6, 6, true),
|
||||||
|
getTestInfo(10, 10, true),
|
||||||
|
getTestInfo(5, 15, true)
|
||||||
|
};
|
||||||
|
DouglasPeucker dp;
|
||||||
|
for (unsigned z = 0; z < DOUGLAS_PEUCKER_THRESHOLDS.size(); z++)
|
||||||
|
{
|
||||||
|
dp.Run(info, z);
|
||||||
|
for (const auto& i : info)
|
||||||
|
{
|
||||||
|
BOOST_CHECK_EQUAL(i.necessary, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
BOOST_AUTO_TEST_CASE(remove_second_node_test)
|
||||||
|
{
|
||||||
|
DouglasPeucker dp;
|
||||||
|
for (unsigned z = 0; z < DOUGLAS_PEUCKER_THRESHOLDS.size(); z++)
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* x--x
|
||||||
|
* | \
|
||||||
|
* x-x x
|
||||||
|
* |
|
||||||
|
* x
|
||||||
|
*/
|
||||||
|
std::vector<SegmentInformation> info = {
|
||||||
|
getTestInfo(5 * COORDINATE_PRECISION,
|
||||||
|
5 * COORDINATE_PRECISION, true),
|
||||||
|
getTestInfo(5 * COORDINATE_PRECISION,
|
||||||
|
5 * COORDINATE_PRECISION + DOUGLAS_PEUCKER_THRESHOLDS[z], false),
|
||||||
|
getTestInfo(10 * COORDINATE_PRECISION,
|
||||||
|
10 * COORDINATE_PRECISION, false),
|
||||||
|
getTestInfo(10 * COORDINATE_PRECISION,
|
||||||
|
10 + COORDINATE_PRECISION + DOUGLAS_PEUCKER_THRESHOLDS[z] * 2, false),
|
||||||
|
getTestInfo(5 * COORDINATE_PRECISION,
|
||||||
|
15 * COORDINATE_PRECISION, false),
|
||||||
|
getTestInfo(5 * COORDINATE_PRECISION + DOUGLAS_PEUCKER_THRESHOLDS[z],
|
||||||
|
15 * COORDINATE_PRECISION, true),
|
||||||
|
};
|
||||||
|
BOOST_TEST_MESSAGE("Threshold (" << z << "): " << DOUGLAS_PEUCKER_THRESHOLDS[z]);
|
||||||
|
dp.Run(info, z);
|
||||||
|
BOOST_CHECK_EQUAL(info[0].necessary, true);
|
||||||
|
BOOST_CHECK_EQUAL(info[1].necessary, false);
|
||||||
|
BOOST_CHECK_EQUAL(info[2].necessary, true);
|
||||||
|
BOOST_CHECK_EQUAL(info[3].necessary, true);
|
||||||
|
BOOST_CHECK_EQUAL(info[4].necessary, false);
|
||||||
|
BOOST_CHECK_EQUAL(info[5].necessary, true);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
BOOST_AUTO_TEST_SUITE_END()
|
||||||
@@ -0,0 +1,35 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#define BOOST_TEST_MODULE algorithm tests
|
||||||
|
|
||||||
|
#include <boost/test/unit_test.hpp>
|
||||||
|
|
||||||
|
/*
|
||||||
|
* This file will contain an automatically generated main function.
|
||||||
|
*/
|
||||||
|
|
||||||
+28
-1
@@ -1,4 +1,31 @@
|
|||||||
#include "../../DataStructures/BinaryHeap.h"
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "../../data_structures/binary_heap.hpp"
|
||||||
#include "../../typedefs.h"
|
#include "../../typedefs.h"
|
||||||
|
|
||||||
#include <boost/test/unit_test.hpp>
|
#include <boost/test/unit_test.hpp>
|
||||||
+28
-1
@@ -1,4 +1,31 @@
|
|||||||
#include "../../DataStructures/RangeTable.h"
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "../../data_structures/range_table.hpp"
|
||||||
#include "../../typedefs.h"
|
#include "../../typedefs.h"
|
||||||
|
|
||||||
#include <boost/test/unit_test.hpp>
|
#include <boost/test/unit_test.hpp>
|
||||||
+28
-1
@@ -1,4 +1,31 @@
|
|||||||
#include "../../DataStructures/StaticGraph.h"
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "../../data_structures/static_graph.hpp"
|
||||||
#include "../../typedefs.h"
|
#include "../../typedefs.h"
|
||||||
|
|
||||||
#include <boost/test/unit_test.hpp>
|
#include <boost/test/unit_test.hpp>
|
||||||
+39
-12
@@ -1,6 +1,33 @@
|
|||||||
#include "../../DataStructures/StaticRTree.h"
|
/*
|
||||||
#include "../../DataStructures/QueryNode.h"
|
|
||||||
#include "../../DataStructures/EdgeBasedNode.h"
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "../../data_structures/static_rtree.hpp"
|
||||||
|
#include "../../data_structures/query_node.hpp"
|
||||||
|
#include "../../data_structures/edge_based_node.hpp"
|
||||||
#include "../../Util/floating_point.hpp"
|
#include "../../Util/floating_point.hpp"
|
||||||
#include "../../typedefs.h"
|
#include "../../typedefs.h"
|
||||||
|
|
||||||
@@ -26,7 +53,7 @@ typedef StaticRTree<TestData,
|
|||||||
TEST_LEAF_NODE_SIZE> TestStaticRTree;
|
TEST_LEAF_NODE_SIZE> TestStaticRTree;
|
||||||
|
|
||||||
// Choosen by a fair W20 dice roll (this value is completely arbitrary)
|
// Choosen by a fair W20 dice roll (this value is completely arbitrary)
|
||||||
constexpr unsigned RANDOM_SEED = 15;
|
constexpr unsigned RANDOM_SEED = 42;
|
||||||
static const int32_t WORLD_MIN_LAT = -90 * COORDINATE_PRECISION;
|
static const int32_t WORLD_MIN_LAT = -90 * COORDINATE_PRECISION;
|
||||||
static const int32_t WORLD_MAX_LAT = 90 * COORDINATE_PRECISION;
|
static const int32_t WORLD_MAX_LAT = 90 * COORDINATE_PRECISION;
|
||||||
static const int32_t WORLD_MIN_LON = -180 * COORDINATE_PRECISION;
|
static const int32_t WORLD_MIN_LON = -180 * COORDINATE_PRECISION;
|
||||||
@@ -74,7 +101,7 @@ class LinearSearchNN
|
|||||||
}
|
}
|
||||||
|
|
||||||
result_coordinate = min_coord;
|
result_coordinate = min_coord;
|
||||||
return result_coordinate.isValid();
|
return result_coordinate.is_valid();
|
||||||
}
|
}
|
||||||
|
|
||||||
bool FindPhantomNodeForCoordinate(const FixedPointCoordinate &input_coordinate,
|
bool FindPhantomNodeForCoordinate(const FixedPointCoordinate &input_coordinate,
|
||||||
@@ -116,7 +143,7 @@ class LinearSearchNN
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (result_phantom_node.location.isValid())
|
if (result_phantom_node.location.is_valid())
|
||||||
{
|
{
|
||||||
// Hack to fix rounding errors and wandering via nodes.
|
// Hack to fix rounding errors and wandering via nodes.
|
||||||
if (1 == std::abs(input_coordinate.lon - result_phantom_node.location.lon))
|
if (1 == std::abs(input_coordinate.lon - result_phantom_node.location.lon))
|
||||||
@@ -144,7 +171,7 @@ class LinearSearchNN
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return result_phantom_node.location.isValid();
|
return result_phantom_node.location.is_valid();
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
@@ -181,7 +208,7 @@ template <unsigned NUM_NODES, unsigned NUM_EDGES> struct RandomGraphFixture
|
|||||||
{
|
{
|
||||||
int lat = lat_udist(g);
|
int lat = lat_udist(g);
|
||||||
int lon = lon_udist(g);
|
int lon = lon_udist(g);
|
||||||
nodes.emplace_back(NodeInfo(lat, lon, i));
|
nodes.emplace_back(QueryNode(lat, lon, i));
|
||||||
coords->emplace_back(FixedPointCoordinate(lat, lon));
|
coords->emplace_back(FixedPointCoordinate(lat, lon));
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -204,7 +231,7 @@ template <unsigned NUM_NODES, unsigned NUM_EDGES> struct RandomGraphFixture
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<NodeInfo> nodes;
|
std::vector<QueryNode> nodes;
|
||||||
std::shared_ptr<std::vector<FixedPointCoordinate>> coords;
|
std::shared_ptr<std::vector<FixedPointCoordinate>> coords;
|
||||||
std::vector<TestData> edges;
|
std::vector<TestData> edges;
|
||||||
};
|
};
|
||||||
@@ -221,7 +248,7 @@ struct GraphFixture
|
|||||||
FixedPointCoordinate c(input_coords[i].first * COORDINATE_PRECISION,
|
FixedPointCoordinate c(input_coords[i].first * COORDINATE_PRECISION,
|
||||||
input_coords[i].second * COORDINATE_PRECISION);
|
input_coords[i].second * COORDINATE_PRECISION);
|
||||||
coords->emplace_back(c);
|
coords->emplace_back(c);
|
||||||
nodes.emplace_back(NodeInfo(c.lat, c.lon, i));
|
nodes.emplace_back(QueryNode(c.lat, c.lon, i));
|
||||||
}
|
}
|
||||||
|
|
||||||
for (const auto &pair : input_edges)
|
for (const auto &pair : input_edges)
|
||||||
@@ -233,7 +260,7 @@ struct GraphFixture
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
std::vector<NodeInfo> nodes;
|
std::vector<QueryNode> nodes;
|
||||||
std::shared_ptr<std::vector<FixedPointCoordinate>> coords;
|
std::shared_ptr<std::vector<FixedPointCoordinate>> coords;
|
||||||
std::vector<TestData> edges;
|
std::vector<TestData> edges;
|
||||||
};
|
};
|
||||||
@@ -316,7 +343,7 @@ void build_rtree(const std::string &prefix,
|
|||||||
boost::filesystem::ofstream node_stream(coords_path, std::ios::binary);
|
boost::filesystem::ofstream node_stream(coords_path, std::ios::binary);
|
||||||
const unsigned num_nodes = fixture->nodes.size();
|
const unsigned num_nodes = fixture->nodes.size();
|
||||||
node_stream.write((char *)&num_nodes, sizeof(unsigned));
|
node_stream.write((char *)&num_nodes, sizeof(unsigned));
|
||||||
node_stream.write((char *)&(fixture->nodes[0]), num_nodes * sizeof(NodeInfo));
|
node_stream.write((char *)&(fixture->nodes[0]), num_nodes * sizeof(QueryNode));
|
||||||
node_stream.close();
|
node_stream.close();
|
||||||
|
|
||||||
RTreeT r(fixture->edges, nodes_path, leaves_path, fixture->nodes);
|
RTreeT r(fixture->edges, nodes_path, leaves_path, fixture->nodes);
|
||||||
@@ -1,3 +1,30 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
#define BOOST_TEST_MODULE datastructure tests
|
#define BOOST_TEST_MODULE datastructure tests
|
||||||
|
|
||||||
#include <boost/test/unit_test.hpp>
|
#include <boost/test/unit_test.hpp>
|
||||||
|
|||||||
@@ -1,73 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef AZIMUTH_H
|
|
||||||
#define AZIMUTH_H
|
|
||||||
|
|
||||||
#include <string>
|
|
||||||
|
|
||||||
struct Azimuth
|
|
||||||
{
|
|
||||||
static std::string Get(const double heading)
|
|
||||||
{
|
|
||||||
if (heading <= 202.5)
|
|
||||||
{
|
|
||||||
if (heading >= 0 && heading <= 22.5)
|
|
||||||
{
|
|
||||||
return "N";
|
|
||||||
}
|
|
||||||
if (heading > 22.5 && heading <= 67.5)
|
|
||||||
{
|
|
||||||
return "NE";
|
|
||||||
}
|
|
||||||
if (heading > 67.5 && heading <= 112.5)
|
|
||||||
{
|
|
||||||
return "E";
|
|
||||||
}
|
|
||||||
if (heading > 112.5 && heading <= 157.5)
|
|
||||||
{
|
|
||||||
return "SE";
|
|
||||||
}
|
|
||||||
return "S";
|
|
||||||
}
|
|
||||||
if (heading > 202.5 && heading <= 247.5)
|
|
||||||
{
|
|
||||||
return "SW";
|
|
||||||
}
|
|
||||||
if (heading > 247.5 && heading <= 292.5)
|
|
||||||
{
|
|
||||||
return "W";
|
|
||||||
}
|
|
||||||
if (heading > 292.5 && heading <= 337.5)
|
|
||||||
{
|
|
||||||
return "NW";
|
|
||||||
}
|
|
||||||
return "N";
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // AZIMUTH_H
|
|
||||||
@@ -50,7 +50,7 @@ namespace filesystem
|
|||||||
// exists. The validate() function must be defined in the same namespace
|
// exists. The validate() function must be defined in the same namespace
|
||||||
// as the target type, (boost::filesystem::path in this case), otherwise
|
// as the target type, (boost::filesystem::path in this case), otherwise
|
||||||
// it is not called
|
// it is not called
|
||||||
// void validate(
|
// inline void validate(
|
||||||
// boost::any & v,
|
// boost::any & v,
|
||||||
// const std::vector<std::string> & values,
|
// const std::vector<std::string> & values,
|
||||||
// boost::filesystem::path *,
|
// boost::filesystem::path *,
|
||||||
@@ -68,7 +68,7 @@ namespace filesystem
|
|||||||
|
|
||||||
// adapted from:
|
// adapted from:
|
||||||
// http://stackoverflow.com/questions/1746136/how-do-i-normalize-a-pathname-using-boostfilesystem
|
// http://stackoverflow.com/questions/1746136/how-do-i-normalize-a-pathname-using-boostfilesystem
|
||||||
boost::filesystem::path
|
inline boost::filesystem::path
|
||||||
portable_canonical(const boost::filesystem::path &relative_path,
|
portable_canonical(const boost::filesystem::path &relative_path,
|
||||||
const boost::filesystem::path ¤t_path = boost::filesystem::current_path())
|
const boost::filesystem::path ¤t_path = boost::filesystem::current_path())
|
||||||
{
|
{
|
||||||
@@ -115,7 +115,7 @@ portable_canonical(const boost::filesystem::path &relative_path,
|
|||||||
|
|
||||||
#if BOOST_FILESYSTEM_VERSION < 3
|
#if BOOST_FILESYSTEM_VERSION < 3
|
||||||
|
|
||||||
path temp_directory_path()
|
inline path temp_directory_path()
|
||||||
{
|
{
|
||||||
char *buffer;
|
char *buffer;
|
||||||
buffer = tmpnam(nullptr);
|
buffer = tmpnam(nullptr);
|
||||||
@@ -123,7 +123,7 @@ path temp_directory_path()
|
|||||||
return path(buffer);
|
return path(buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
path unique_path(const path &) { return temp_directory_path(); }
|
inline path unique_path(const path &) { return temp_directory_path(); }
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
@@ -133,7 +133,7 @@ path unique_path(const path &) { return temp_directory_path(); }
|
|||||||
#define BOOST_FILESYSTEM_VERSION 3
|
#define BOOST_FILESYSTEM_VERSION 3
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
void AssertPathExists(const boost::filesystem::path &path)
|
inline void AssertPathExists(const boost::filesystem::path &path)
|
||||||
{
|
{
|
||||||
if (!boost::filesystem::is_regular_file(path))
|
if (!boost::filesystem::is_regular_file(path))
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -42,7 +42,6 @@ class FingerPrint
|
|||||||
bool TestGraphUtil(const FingerPrint &other) const;
|
bool TestGraphUtil(const FingerPrint &other) const;
|
||||||
bool TestPrepare(const FingerPrint &other) const;
|
bool TestPrepare(const FingerPrint &other) const;
|
||||||
bool TestRTree(const FingerPrint &other) const;
|
bool TestRTree(const FingerPrint &other) const;
|
||||||
bool TestNodeInfo(const FingerPrint &other) const;
|
|
||||||
bool TestQueryObjects(const FingerPrint &other) const;
|
bool TestQueryObjects(const FingerPrint &other) const;
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|||||||
@@ -146,12 +146,6 @@ inline std::size_t URIDecode(const std::string &input, std::string &output)
|
|||||||
|
|
||||||
inline std::size_t URIDecodeInPlace(std::string &URI) { return URIDecode(URI, URI); }
|
inline std::size_t URIDecodeInPlace(std::string &URI) { return URIDecode(URI, URI); }
|
||||||
|
|
||||||
// TODO: remove after switch to libosmium
|
|
||||||
inline bool StringStartsWith(const std::string &input, const std::string &prefix)
|
|
||||||
{
|
|
||||||
return boost::starts_with(input, prefix);
|
|
||||||
}
|
|
||||||
|
|
||||||
inline std::string GetRandomString()
|
inline std::string GetRandomString()
|
||||||
{
|
{
|
||||||
std::string s;
|
std::string s;
|
||||||
|
|||||||
@@ -1,39 +0,0 @@
|
|||||||
/*
|
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
|
||||||
All rights reserved.
|
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
|
||||||
are permitted provided that the following conditions are met:
|
|
||||||
|
|
||||||
Redistributions of source code must retain the above copyright notice, this list
|
|
||||||
of conditions and the following disclaimer.
|
|
||||||
Redistributions in binary form must reproduce the above copyright notice, this
|
|
||||||
list of conditions and the following disclaimer in the documentation and/or
|
|
||||||
other materials provided with the distribution.
|
|
||||||
|
|
||||||
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
|
||||||
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
|
||||||
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
|
||||||
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
|
||||||
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
|
||||||
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
|
||||||
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
|
||||||
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
|
||||||
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
|
||||||
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|
||||||
|
|
||||||
*/
|
|
||||||
|
|
||||||
#ifndef TIMINGUTIL_H
|
|
||||||
#define TIMINGUTIL_H
|
|
||||||
|
|
||||||
#include <chrono>
|
|
||||||
|
|
||||||
#define TIMER_START(_X) auto _X##_start = std::chrono::steady_clock::now(), _X##_stop = _X##_start
|
|
||||||
#define TIMER_STOP(_X) _X##_stop = std::chrono::steady_clock::now()
|
|
||||||
#define TIMER_MSEC(_X) std::chrono::duration_cast<std::chrono::milliseconds>(_X##_stop - _X##_start).count()
|
|
||||||
#define TIMER_SEC(_X) (0.001*std::chrono::duration_cast<std::chrono::milliseconds>(_X##_stop - _X##_start).count())
|
|
||||||
#define TIMER_MIN(_X) std::chrono::duration_cast<std::chrono::minutes>(_X##_stop - _X##_start).count()
|
|
||||||
|
|
||||||
#endif // TIMINGUTIL_H
|
|
||||||
@@ -722,7 +722,7 @@ constexpr unsigned short atan_table[4096] = {
|
|||||||
// max value is pi/4
|
// max value is pi/4
|
||||||
constexpr double SCALING_FACTOR = 4. / M_PI * 0xFFFF;
|
constexpr double SCALING_FACTOR = 4. / M_PI * 0xFFFF;
|
||||||
|
|
||||||
double atan2_lookup(double y, double x)
|
inline double atan2_lookup(double y, double x)
|
||||||
{
|
{
|
||||||
if (std::abs(x) < std::numeric_limits<double>::epsilon())
|
if (std::abs(x) < std::numeric_limits<double>::epsilon())
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -25,33 +25,41 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef MACHINE_INFO_H
|
#include "bearing.hpp"
|
||||||
#define MACHINE_INFO_H
|
|
||||||
|
|
||||||
enum Endianness
|
std::string Bearing::Get(const double heading)
|
||||||
{ LittleEndian = 1,
|
|
||||||
BigEndian = 2 };
|
|
||||||
|
|
||||||
// Function is optimized to a single 'mov eax,1' on GCC, clang and icc using -O3
|
|
||||||
Endianness GetMachineEndianness()
|
|
||||||
{
|
{
|
||||||
int i(1);
|
if (heading <= 202.5)
|
||||||
char *p = (char *)&i;
|
|
||||||
if (1 == p[0])
|
|
||||||
{
|
{
|
||||||
return LittleEndian;
|
if (heading >= 0. && heading <= 22.5)
|
||||||
}
|
|
||||||
return BigEndian;
|
|
||||||
}
|
|
||||||
|
|
||||||
// Reverses Network Byte Order into something usable, compiles down to a bswap-mov combination
|
|
||||||
unsigned SwapEndian(unsigned x)
|
|
||||||
{
|
|
||||||
if (GetMachineEndianness() == LittleEndian)
|
|
||||||
{
|
{
|
||||||
return ((x >> 24) | ((x << 8) & 0x00FF0000) | ((x >> 8) & 0x0000FF00) | (x << 24));
|
return "N";
|
||||||
}
|
}
|
||||||
return x;
|
if (heading > 22.5 && heading <= 67.5)
|
||||||
|
{
|
||||||
|
return "NE";
|
||||||
|
}
|
||||||
|
if (heading > 67.5 && heading <= 112.5)
|
||||||
|
{
|
||||||
|
return "E";
|
||||||
|
}
|
||||||
|
if (heading > 112.5 && heading <= 157.5)
|
||||||
|
{
|
||||||
|
return "SE";
|
||||||
|
}
|
||||||
|
return "S";
|
||||||
|
}
|
||||||
|
if (heading > 202.5 && heading <= 247.5)
|
||||||
|
{
|
||||||
|
return "SW";
|
||||||
|
}
|
||||||
|
if (heading > 247.5 && heading <= 292.5)
|
||||||
|
{
|
||||||
|
return "W";
|
||||||
|
}
|
||||||
|
if (heading > 292.5 && heading <= 337.5)
|
||||||
|
{
|
||||||
|
return "NW";
|
||||||
|
}
|
||||||
|
return "N";
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif // MACHINE_INFO_H
|
|
||||||
@@ -0,0 +1,38 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef BEARING_HPP_
|
||||||
|
#define BEARING_HPP_
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
|
||||||
|
struct Bearing
|
||||||
|
{
|
||||||
|
static std::string Get(const double heading);
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // BEARING_HPP_
|
||||||
+9
-2
@@ -41,13 +41,13 @@ template <typename T> void sort_unique_resize(std::vector<T> &vector)
|
|||||||
vector.resize(number_of_unique_elements);
|
vector.resize(number_of_unique_elements);
|
||||||
}
|
}
|
||||||
|
|
||||||
// template <typename T> void sort_unique_resize_shrink_vector(std::vector<T> &vector)
|
// template <typename T> inline void sort_unique_resize_shrink_vector(std::vector<T> &vector)
|
||||||
// {
|
// {
|
||||||
// sort_unique_resize(vector);
|
// sort_unique_resize(vector);
|
||||||
// vector.shrink_to_fit();
|
// vector.shrink_to_fit();
|
||||||
// }
|
// }
|
||||||
|
|
||||||
// template <typename T> void remove_consecutive_duplicates_from_vector(std::vector<T> &vector)
|
// template <typename T> inline void remove_consecutive_duplicates_from_vector(std::vector<T> &vector)
|
||||||
// {
|
// {
|
||||||
// const auto number_of_unique_elements = std::unique(vector.begin(), vector.end()) - vector.begin();
|
// const auto number_of_unique_elements = std::unique(vector.begin(), vector.end()) - vector.begin();
|
||||||
// vector.resize(number_of_unique_elements);
|
// vector.resize(number_of_unique_elements);
|
||||||
@@ -71,5 +71,12 @@ Function for_each_pair(ForwardIterator begin, ForwardIterator end, Function func
|
|||||||
}
|
}
|
||||||
return function;
|
return function;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
template <class ContainerT, typename Function>
|
||||||
|
Function for_each_pair(ContainerT &container, Function function)
|
||||||
|
{
|
||||||
|
return for_each_pair(std::begin(container), std::end(container), function);
|
||||||
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
#endif /* CONTAINER_HPP_ */
|
#endif /* CONTAINER_HPP_ */
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -29,10 +29,10 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
#define GRAPHLOADER_H
|
#define GRAPHLOADER_H
|
||||||
|
|
||||||
#include "OSRMException.h"
|
#include "OSRMException.h"
|
||||||
#include "../DataStructures/ImportNode.h"
|
#include "../data_structures/external_memory_node.hpp"
|
||||||
#include "../DataStructures/ImportEdge.h"
|
#include "../data_structures/import_edge.hpp"
|
||||||
#include "../DataStructures/QueryNode.h"
|
#include "../data_structures/query_node.hpp"
|
||||||
#include "../DataStructures/Restriction.h"
|
#include "../data_structures/restriction.hpp"
|
||||||
#include "../Util/simple_logger.hpp"
|
#include "../Util/simple_logger.hpp"
|
||||||
#include "../Util/FingerPrint.h"
|
#include "../Util/FingerPrint.h"
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
@@ -57,7 +57,7 @@ NodeID readBinaryOSRMGraphFromStream(std::istream &input_stream,
|
|||||||
std::vector<EdgeT> &edge_list,
|
std::vector<EdgeT> &edge_list,
|
||||||
std::vector<NodeID> &barrier_node_list,
|
std::vector<NodeID> &barrier_node_list,
|
||||||
std::vector<NodeID> &traffic_light_node_list,
|
std::vector<NodeID> &traffic_light_node_list,
|
||||||
std::vector<NodeInfo> *int_to_ext_node_id_map,
|
std::vector<QueryNode> *int_to_ext_node_id_map,
|
||||||
std::vector<TurnRestriction> &restriction_list)
|
std::vector<TurnRestriction> &restriction_list)
|
||||||
{
|
{
|
||||||
const FingerPrint fingerprint_orig;
|
const FingerPrint fingerprint_orig;
|
||||||
@@ -70,23 +70,23 @@ NodeID readBinaryOSRMGraphFromStream(std::istream &input_stream,
|
|||||||
"Reprocess to get rid of this warning.";
|
"Reprocess to get rid of this warning.";
|
||||||
}
|
}
|
||||||
|
|
||||||
NodeID n, source, target;
|
|
||||||
EdgeID m;
|
|
||||||
short dir; // direction (0 = open, 1 = forward, 2+ = open)
|
|
||||||
std::unordered_map<NodeID, NodeID> ext_to_int_id_map;
|
std::unordered_map<NodeID, NodeID> ext_to_int_id_map;
|
||||||
|
|
||||||
|
NodeID n;
|
||||||
input_stream.read((char *)&n, sizeof(NodeID));
|
input_stream.read((char *)&n, sizeof(NodeID));
|
||||||
SimpleLogger().Write() << "Importing n = " << n << " nodes ";
|
SimpleLogger().Write() << "Importing n = " << n << " nodes ";
|
||||||
|
|
||||||
ExternalMemoryNode current_node;
|
ExternalMemoryNode current_node;
|
||||||
for (NodeID i = 0; i < n; ++i)
|
for (NodeID i = 0; i < n; ++i)
|
||||||
{
|
{
|
||||||
input_stream.read((char *)¤t_node, sizeof(ExternalMemoryNode));
|
input_stream.read((char *)¤t_node, sizeof(ExternalMemoryNode));
|
||||||
int_to_ext_node_id_map->emplace_back(current_node.lat, current_node.lon, current_node.node_id);
|
int_to_ext_node_id_map->emplace_back(current_node.lat, current_node.lon, current_node.node_id);
|
||||||
ext_to_int_id_map.emplace(current_node.node_id, i);
|
ext_to_int_id_map.emplace(current_node.node_id, i);
|
||||||
if (current_node.bollard)
|
if (current_node.barrier)
|
||||||
{
|
{
|
||||||
barrier_node_list.emplace_back(i);
|
barrier_node_list.emplace_back(i);
|
||||||
}
|
}
|
||||||
if (current_node.trafficLight)
|
if (current_node.traffic_lights)
|
||||||
{
|
{
|
||||||
traffic_light_node_list.emplace_back(i);
|
traffic_light_node_list.emplace_back(i);
|
||||||
}
|
}
|
||||||
@@ -95,41 +95,48 @@ NodeID readBinaryOSRMGraphFromStream(std::istream &input_stream,
|
|||||||
// tighten vector sizes
|
// tighten vector sizes
|
||||||
barrier_node_list.shrink_to_fit();
|
barrier_node_list.shrink_to_fit();
|
||||||
traffic_light_node_list.shrink_to_fit();
|
traffic_light_node_list.shrink_to_fit();
|
||||||
input_stream.read((char *)&m, sizeof(unsigned));
|
|
||||||
SimpleLogger().Write() << " and " << m << " edges ";
|
// renumber nodes in turn restrictions
|
||||||
for (TurnRestriction ¤t_restriction : restriction_list)
|
for (TurnRestriction ¤t_restriction : restriction_list)
|
||||||
{
|
{
|
||||||
auto internal_id_iter = ext_to_int_id_map.find(current_restriction.fromNode);
|
auto internal_id_iter = ext_to_int_id_map.find(current_restriction.from.node);
|
||||||
if (internal_id_iter == ext_to_int_id_map.end())
|
if (internal_id_iter == ext_to_int_id_map.end())
|
||||||
{
|
{
|
||||||
SimpleLogger().Write(logDEBUG) << "Unmapped from Node of restriction";
|
SimpleLogger().Write(logDEBUG) << "Unmapped from Node of restriction";
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
current_restriction.fromNode = internal_id_iter->second;
|
current_restriction.from.node = internal_id_iter->second;
|
||||||
|
|
||||||
internal_id_iter = ext_to_int_id_map.find(current_restriction.viaNode);
|
internal_id_iter = ext_to_int_id_map.find(current_restriction.via.node);
|
||||||
if (internal_id_iter == ext_to_int_id_map.end())
|
if (internal_id_iter == ext_to_int_id_map.end())
|
||||||
{
|
{
|
||||||
SimpleLogger().Write(logDEBUG) << "Unmapped via node of restriction";
|
SimpleLogger().Write(logDEBUG) << "Unmapped via node of restriction";
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
current_restriction.viaNode = internal_id_iter->second;
|
current_restriction.via.node = internal_id_iter->second;
|
||||||
|
|
||||||
internal_id_iter = ext_to_int_id_map.find(current_restriction.toNode);
|
internal_id_iter = ext_to_int_id_map.find(current_restriction.to.node);
|
||||||
if (internal_id_iter == ext_to_int_id_map.end())
|
if (internal_id_iter == ext_to_int_id_map.end())
|
||||||
{
|
{
|
||||||
SimpleLogger().Write(logDEBUG) << "Unmapped to node of restriction";
|
SimpleLogger().Write(logDEBUG) << "Unmapped to node of restriction";
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
current_restriction.toNode = internal_id_iter->second;
|
current_restriction.to.node = internal_id_iter->second;
|
||||||
}
|
}
|
||||||
|
|
||||||
edge_list.reserve(m);
|
|
||||||
EdgeWeight weight;
|
EdgeWeight weight;
|
||||||
NodeID nameID;
|
NodeID source, target;
|
||||||
|
unsigned nameID;
|
||||||
int length;
|
int length;
|
||||||
|
short dir; // direction (0 = open, 1 = forward, 2+ = open)
|
||||||
bool is_roundabout, ignore_in_grid, is_access_restricted, is_split;
|
bool is_roundabout, ignore_in_grid, is_access_restricted, is_split;
|
||||||
TravelMode travel_mode;
|
TravelMode travel_mode;
|
||||||
|
|
||||||
|
EdgeID m;
|
||||||
|
input_stream.read((char *)&m, sizeof(unsigned));
|
||||||
|
edge_list.reserve(m);
|
||||||
|
SimpleLogger().Write() << " and " << m << " edges ";
|
||||||
|
|
||||||
for (EdgeID i = 0; i < m; ++i)
|
for (EdgeID i = 0; i < m; ++i)
|
||||||
{
|
{
|
||||||
input_stream.read((char *)&source, sizeof(unsigned));
|
input_stream.read((char *)&source, sizeof(unsigned));
|
||||||
@@ -178,7 +185,8 @@ NodeID readBinaryOSRMGraphFromStream(std::istream &input_stream,
|
|||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
target = internal_id_iter->second;
|
target = internal_id_iter->second;
|
||||||
BOOST_ASSERT_MSG(source != UINT_MAX && target != UINT_MAX, "nonexisting source or target");
|
BOOST_ASSERT_MSG(source != SPECIAL_NODEID && target != SPECIAL_NODEID,
|
||||||
|
"nonexisting source or target");
|
||||||
|
|
||||||
if (source > target)
|
if (source > target)
|
||||||
{
|
{
|
||||||
@@ -198,8 +206,10 @@ NodeID readBinaryOSRMGraphFromStream(std::istream &input_stream,
|
|||||||
travel_mode,
|
travel_mode,
|
||||||
is_split);
|
is_split);
|
||||||
}
|
}
|
||||||
|
ext_to_int_id_map.clear();
|
||||||
|
|
||||||
tbb::parallel_sort(edge_list.begin(), edge_list.end());
|
tbb::parallel_sort(edge_list.begin(), edge_list.end());
|
||||||
|
|
||||||
for (unsigned i = 1; i < edge_list.size(); ++i)
|
for (unsigned i = 1; i < edge_list.size(); ++i)
|
||||||
{
|
{
|
||||||
if ((edge_list[i - 1].target == edge_list[i].target) &&
|
if ((edge_list[i - 1].target == edge_list[i].target) &&
|
||||||
@@ -210,22 +220,22 @@ NodeID readBinaryOSRMGraphFromStream(std::istream &input_stream,
|
|||||||
(edge_list[i - 1].backward == edge_list[i].backward);
|
(edge_list[i - 1].backward == edge_list[i].backward);
|
||||||
const bool edge_flags_are_superset1 =
|
const bool edge_flags_are_superset1 =
|
||||||
(edge_list[i - 1].forward && edge_list[i - 1].backward) &&
|
(edge_list[i - 1].forward && edge_list[i - 1].backward) &&
|
||||||
(edge_list[i].backward != edge_list[i].backward);
|
(edge_list[i].forward != edge_list[i].backward);
|
||||||
const bool edge_flags_are_superset_2 =
|
const bool edge_flags_are_superset_2 =
|
||||||
(edge_list[i].forward && edge_list[i].backward) &&
|
(edge_list[i].forward && edge_list[i].backward) &&
|
||||||
(edge_list[i - 1].backward != edge_list[i - 1].backward);
|
(edge_list[i - 1].forward != edge_list[i - 1].backward);
|
||||||
|
|
||||||
if (edge_flags_equivalent)
|
if (edge_flags_equivalent)
|
||||||
{
|
{
|
||||||
edge_list[i].weight = std::min(edge_list[i - 1].weight, edge_list[i].weight);
|
edge_list[i].weight = std::min(edge_list[i - 1].weight, edge_list[i].weight);
|
||||||
edge_list[i - 1].source = UINT_MAX;
|
edge_list[i - 1].source = SPECIAL_NODEID;
|
||||||
}
|
}
|
||||||
else if (edge_flags_are_superset1)
|
else if (edge_flags_are_superset1)
|
||||||
{
|
{
|
||||||
if (edge_list[i - 1].weight <= edge_list[i].weight)
|
if (edge_list[i - 1].weight <= edge_list[i].weight)
|
||||||
{
|
{
|
||||||
// edge i-1 is smaller and goes in both directions. Throw away the other edge
|
// edge i-1 is smaller and goes in both directions. Throw away the other edge
|
||||||
edge_list[i].source = UINT_MAX;
|
edge_list[i].source = SPECIAL_NODEID;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@@ -247,132 +257,22 @@ NodeID readBinaryOSRMGraphFromStream(std::istream &input_stream,
|
|||||||
else
|
else
|
||||||
{
|
{
|
||||||
// edge i is smaller and goes in both direction. Throw away edge i-1
|
// edge i is smaller and goes in both direction. Throw away edge i-1
|
||||||
edge_list[i - 1].source = UINT_MAX;
|
edge_list[i - 1].source = SPECIAL_NODEID;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
const auto new_end_iter = std::remove_if(edge_list.begin(),
|
const auto new_end_iter = std::remove_if(edge_list.begin(), edge_list.end(), [] (const EdgeT &edge)
|
||||||
edge_list.end(),
|
{
|
||||||
[](const EdgeT &edge)
|
return edge.source == SPECIAL_NODEID ||
|
||||||
{ return edge.source == SPECIAL_NODEID; });
|
edge.target == SPECIAL_NODEID;
|
||||||
ext_to_int_id_map.clear();
|
});
|
||||||
edge_list.erase(new_end_iter, edge_list.end()); // remove excess candidates.
|
edge_list.erase(new_end_iter, edge_list.end()); // remove excess candidates.
|
||||||
edge_list.shrink_to_fit();
|
edge_list.shrink_to_fit();
|
||||||
SimpleLogger().Write() << "Graph loaded ok and has " << edge_list.size() << " edges";
|
SimpleLogger().Write() << "Graph loaded ok and has " << edge_list.size() << " edges";
|
||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
|
||||||
template <typename EdgeT, typename CoordinateT>
|
|
||||||
NodeID readBinaryOSRMGraphFromStream(std::istream &input_stream,
|
|
||||||
std::vector<EdgeT> &edge_list,
|
|
||||||
std::vector<CoordinateT> & coordinate_list)
|
|
||||||
{
|
|
||||||
const FingerPrint fingerprint_orig;
|
|
||||||
FingerPrint fingerprint_loaded;
|
|
||||||
input_stream.read((char *)&fingerprint_loaded, sizeof(FingerPrint));
|
|
||||||
|
|
||||||
if (!fingerprint_loaded.TestGraphUtil(fingerprint_orig))
|
|
||||||
{
|
|
||||||
SimpleLogger().Write(logWARNING) << ".osrm was prepared with different build.\n"
|
|
||||||
"Reprocess to get rid of this warning.";
|
|
||||||
}
|
|
||||||
|
|
||||||
NodeID n, source, target;
|
|
||||||
EdgeID m;
|
|
||||||
short dir; // direction (0 = open, 1 = forward, 2+ = open)
|
|
||||||
std::unordered_map<NodeID, NodeID> ext_to_int_id_map;
|
|
||||||
|
|
||||||
input_stream.read((char *)&n, sizeof(NodeID));
|
|
||||||
SimpleLogger().Write() << "Importing n = " << n << " nodes ";
|
|
||||||
ExternalMemoryNode current_node;
|
|
||||||
for (NodeID i = 0; i < n; ++i)
|
|
||||||
{
|
|
||||||
input_stream.read((char *)¤t_node, sizeof(ExternalMemoryNode));
|
|
||||||
coordinate_list.emplace_back(current_node.lat, current_node.lon);
|
|
||||||
ext_to_int_id_map.emplace(current_node.node_id, i);
|
|
||||||
}
|
|
||||||
|
|
||||||
input_stream.read((char *)&m, sizeof(unsigned));
|
|
||||||
SimpleLogger().Write() << " and " << m << " edges ";
|
|
||||||
|
|
||||||
edge_list.reserve(m);
|
|
||||||
EdgeWeight weight;
|
|
||||||
NodeID nameID;
|
|
||||||
int length;
|
|
||||||
bool is_roundabout, ignore_in_grid, is_access_restricted, is_split;
|
|
||||||
TravelMode travel_mode;
|
|
||||||
|
|
||||||
for (EdgeID i = 0; i < m; ++i)
|
|
||||||
{
|
|
||||||
input_stream.read((char *)&source, sizeof(unsigned));
|
|
||||||
input_stream.read((char *)&target, sizeof(unsigned));
|
|
||||||
input_stream.read((char *)&length, sizeof(int));
|
|
||||||
input_stream.read((char *)&dir, sizeof(short));
|
|
||||||
input_stream.read((char *)&weight, sizeof(int));
|
|
||||||
input_stream.read((char *)&nameID, sizeof(unsigned));
|
|
||||||
input_stream.read((char *)&is_roundabout, sizeof(bool));
|
|
||||||
input_stream.read((char *)&ignore_in_grid, sizeof(bool));
|
|
||||||
input_stream.read((char *)&is_access_restricted, sizeof(bool));
|
|
||||||
input_stream.read((char *)&travel_mode, sizeof(TravelMode));
|
|
||||||
input_stream.read((char *)&is_split, sizeof(bool));
|
|
||||||
|
|
||||||
BOOST_ASSERT_MSG(length > 0, "loaded null length edge");
|
|
||||||
BOOST_ASSERT_MSG(weight > 0, "loaded null weight");
|
|
||||||
BOOST_ASSERT_MSG(0 <= dir && dir <= 2, "loaded bogus direction");
|
|
||||||
|
|
||||||
// translate the external NodeIDs to internal IDs
|
|
||||||
auto internal_id_iter = ext_to_int_id_map.find(source);
|
|
||||||
if (ext_to_int_id_map.find(source) == ext_to_int_id_map.end())
|
|
||||||
{
|
|
||||||
#ifndef NDEBUG
|
|
||||||
SimpleLogger().Write(logWARNING) << " unresolved source NodeID: " << source;
|
|
||||||
#endif
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
source = internal_id_iter->second;
|
|
||||||
internal_id_iter = ext_to_int_id_map.find(target);
|
|
||||||
if (ext_to_int_id_map.find(target) == ext_to_int_id_map.end())
|
|
||||||
{
|
|
||||||
#ifndef NDEBUG
|
|
||||||
SimpleLogger().Write(logWARNING) << "unresolved target NodeID : " << target;
|
|
||||||
#endif
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
target = internal_id_iter->second;
|
|
||||||
BOOST_ASSERT_MSG(source != UINT_MAX && target != UINT_MAX, "nonexisting source or target");
|
|
||||||
|
|
||||||
if (source > target)
|
|
||||||
{
|
|
||||||
std::swap(source, target);
|
|
||||||
}
|
|
||||||
|
|
||||||
edge_list.emplace_back(source,
|
|
||||||
target);
|
|
||||||
}
|
|
||||||
|
|
||||||
tbb::parallel_sort(edge_list.begin(), edge_list.end());
|
|
||||||
for (unsigned i = 1; i < edge_list.size(); ++i)
|
|
||||||
{
|
|
||||||
if ((edge_list[i - 1].target == edge_list[i].target) &&
|
|
||||||
(edge_list[i - 1].source == edge_list[i].source))
|
|
||||||
{
|
|
||||||
edge_list[i].distance = std::min(edge_list[i - 1].distance, edge_list[i].distance);
|
|
||||||
edge_list[i - 1].source = UINT_MAX;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
const auto new_end_iter = std::remove_if(edge_list.begin(),
|
|
||||||
edge_list.end(),
|
|
||||||
[](const EdgeT &edge)
|
|
||||||
{ return edge.source == SPECIAL_NODEID; });
|
|
||||||
ext_to_int_id_map.clear();
|
|
||||||
edge_list.erase(new_end_iter, edge_list.end()); // remove excess candidates.
|
|
||||||
edge_list.shrink_to_fit();
|
|
||||||
SimpleLogger().Write() << "Graph loaded ok and has " << n << " nodes and " << edge_list.size() << " edges";
|
|
||||||
return n;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
template <typename NodeT, typename EdgeT>
|
template <typename NodeT, typename EdgeT>
|
||||||
unsigned readHSGRFromStream(const boost::filesystem::path &hsgr_file,
|
unsigned readHSGRFromStream(const boost::filesystem::path &hsgr_file,
|
||||||
std::vector<NodeT> &node_list,
|
std::vector<NodeT> &node_list,
|
||||||
@@ -25,54 +25,48 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef HASH_TABLE_H
|
#ifndef RANGE_HPP_
|
||||||
#define HASH_TABLE_H
|
#define RANGE_HPP_
|
||||||
|
|
||||||
#include <vector>
|
namespace osrm
|
||||||
|
{
|
||||||
template <typename Key, typename Value>
|
namespace util
|
||||||
class HashTable
|
{
|
||||||
|
template <typename Iterator> class Range
|
||||||
{
|
{
|
||||||
private:
|
|
||||||
using KeyValPair = std::pair<Key, Value>;
|
|
||||||
std::vector<KeyValPair> table;
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
HashTable() {}
|
Range(Iterator begin, Iterator end) : begin_(begin), end_(end) {}
|
||||||
|
|
||||||
inline void Add(Key const &key, Value const &value)
|
Iterator begin() const { return begin_; }
|
||||||
{
|
Iterator end() const { return end_; }
|
||||||
table.emplace_back(std::move(key), std::move(value));
|
|
||||||
}
|
|
||||||
|
|
||||||
inline void Clear()
|
private:
|
||||||
{
|
Iterator begin_;
|
||||||
table.clear();
|
Iterator end_;
|
||||||
}
|
|
||||||
|
|
||||||
inline const Value Find(Key const &key) const
|
|
||||||
{
|
|
||||||
for (const auto &key_val_pair : table)
|
|
||||||
{
|
|
||||||
if (key_val_pair.first == key)
|
|
||||||
{
|
|
||||||
return key_val_pair.second;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return Value();
|
|
||||||
}
|
|
||||||
|
|
||||||
inline const bool Holds(Key const &key) const
|
|
||||||
{
|
|
||||||
for (const auto &key_val_pair : table)
|
|
||||||
{
|
|
||||||
if (key_val_pair.first == key)
|
|
||||||
{
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return false;
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* HASH_TABLE_H */
|
// Convenience functions for template parameter inference,
|
||||||
|
// akin to std::make_pair.
|
||||||
|
|
||||||
|
template <typename Iterator> Range<Iterator> range(Iterator begin, Iterator end)
|
||||||
|
{
|
||||||
|
return Range<Iterator>(begin, end);
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename Reversable>
|
||||||
|
Range<typename Reversable::reverse_iterator> reverse(Reversable *reversable)
|
||||||
|
{
|
||||||
|
return Range<typename Reversable::reverse_iterator>(reversable->rbegin(), reversable->rend());
|
||||||
|
}
|
||||||
|
|
||||||
|
template <typename ConstReversable>
|
||||||
|
Range<typename ConstReversable::const_reverse_iterator>
|
||||||
|
const_reverse(const ConstReversable *const_reversable)
|
||||||
|
{
|
||||||
|
return Range<typename ConstReversable::const_reverse_iterator>(const_reversable->crbegin(),
|
||||||
|
const_reversable->crend());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif // RANGE_HPP_
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -28,67 +28,13 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
// based on
|
// based on
|
||||||
// https://svn.apache.org/repos/asf/mesos/tags/release-0.9.0-incubating-RC0/src/common/json.hpp
|
// https://svn.apache.org/repos/asf/mesos/tags/release-0.9.0-incubating-RC0/src/common/json.hpp
|
||||||
|
|
||||||
#ifndef JSON_CONTAINER_H
|
#ifndef JSON_RENDERER_HPP
|
||||||
#define JSON_CONTAINER_H
|
#define JSON_RENDERER_HPP
|
||||||
|
|
||||||
#include "../ThirdParty/variant/variant.hpp"
|
#include "../data_structures/json_container.hpp"
|
||||||
#include "../Util/cast.hpp"
|
#include "cast.hpp"
|
||||||
|
|
||||||
#include <iostream>
|
namespace JSON {
|
||||||
#include <vector>
|
|
||||||
#include <string>
|
|
||||||
#include <unordered_map>
|
|
||||||
|
|
||||||
namespace JSON
|
|
||||||
{
|
|
||||||
|
|
||||||
struct Object;
|
|
||||||
struct Array;
|
|
||||||
|
|
||||||
struct String
|
|
||||||
{
|
|
||||||
String() {}
|
|
||||||
String(const char *value) : value(value) {}
|
|
||||||
String(const std::string &value) : value(value) {}
|
|
||||||
std::string value;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct Number
|
|
||||||
{
|
|
||||||
Number() {}
|
|
||||||
Number(double value) : value(value) {}
|
|
||||||
double value;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct True
|
|
||||||
{
|
|
||||||
};
|
|
||||||
|
|
||||||
struct False
|
|
||||||
{
|
|
||||||
};
|
|
||||||
|
|
||||||
struct Null
|
|
||||||
{
|
|
||||||
};
|
|
||||||
|
|
||||||
using Value = mapbox::util::variant<String,
|
|
||||||
Number,
|
|
||||||
mapbox::util::recursive_wrapper<Object>,
|
|
||||||
mapbox::util::recursive_wrapper<Array>,
|
|
||||||
True,
|
|
||||||
False,
|
|
||||||
Null>;
|
|
||||||
|
|
||||||
struct Object
|
|
||||||
{
|
|
||||||
std::unordered_map<std::string, Value> values;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct Array
|
|
||||||
{
|
|
||||||
std::vector<Value> values;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct Renderer : mapbox::util::static_visitor<>
|
struct Renderer : mapbox::util::static_visitor<>
|
||||||
{
|
{
|
||||||
@@ -233,4 +179,4 @@ inline void render(std::vector<char> &out, const Object &object)
|
|||||||
|
|
||||||
} // namespace JSON
|
} // namespace JSON
|
||||||
|
|
||||||
#endif // JSON_CONTAINER_H
|
#endif // JSON_RENDERER_HPP
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef LUA_UTIL_H
|
#ifndef LUA_UTIL_HPP
|
||||||
#define LUA_UTIL_H
|
#define LUA_UTIL_HPP
|
||||||
|
|
||||||
extern "C" {
|
extern "C" {
|
||||||
#include <lua.h>
|
#include <lua.h>
|
||||||
@@ -63,4 +63,4 @@ inline void luaAddScriptFolderToLoadPath(lua_State *lua_state, const char *file_
|
|||||||
luaL_dostring(lua_state, lua_code.c_str());
|
luaL_dostring(lua_state, lua_code.c_str());
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif // LUA_UTIL_H
|
#endif // LUA_UTIL_HPP
|
||||||
@@ -0,0 +1,42 @@
|
|||||||
|
/*
|
||||||
|
open source routing machine
|
||||||
|
Copyright (C) Dennis Luxen, others 2010
|
||||||
|
|
||||||
|
This program is free software; you can redistribute it and/or modify
|
||||||
|
it under the terms of the GNU AFFERO General Public License as published by
|
||||||
|
the Free Software Foundation; either version 3 of the License, or
|
||||||
|
any later version.
|
||||||
|
|
||||||
|
This program is distributed in the hope that it will be useful,
|
||||||
|
but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||||
|
GNU General Public License for more details.
|
||||||
|
|
||||||
|
You should have received a copy of the GNU Affero General Public License
|
||||||
|
along with this program; if not, write to the Free Software
|
||||||
|
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
|
||||||
|
or see http://www.gnu.org/licenses/agpl.txt.
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef RANGE_ALGORITHMS_HPP
|
||||||
|
#define RANGE_ALGORITHMS_HPP
|
||||||
|
|
||||||
|
#include <algorithm>
|
||||||
|
|
||||||
|
namespace osrm {
|
||||||
|
|
||||||
|
template<class Container>
|
||||||
|
auto max_element(const Container & c) -> decltype(std::max_element(c.begin(), c.end()))
|
||||||
|
{
|
||||||
|
return std::max_element(c.begin(), c.end());
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class Container>
|
||||||
|
auto max_element(const Container & c) -> decltype(std::max_element(c.cbegin(), c.cend()))
|
||||||
|
{
|
||||||
|
return std::max_element(c.cbegin(), c.cend());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
#endif // RANGE_ALGORITHMS_HPP
|
||||||
@@ -74,16 +74,16 @@ SimpleLogger::SimpleLogger() : level(logINFO) {}
|
|||||||
|
|
||||||
std::mutex &SimpleLogger::get_mutex()
|
std::mutex &SimpleLogger::get_mutex()
|
||||||
{
|
{
|
||||||
static std::mutex m;
|
static std::mutex mtx;
|
||||||
return m;
|
return mtx;
|
||||||
}
|
}
|
||||||
|
|
||||||
std::ostringstream &SimpleLogger::Write(LogLevel l)
|
std::ostringstream &SimpleLogger::Write(LogLevel lvl)
|
||||||
{
|
{
|
||||||
std::lock_guard<std::mutex> lock(get_mutex());
|
std::lock_guard<std::mutex> lock(get_mutex());
|
||||||
try
|
try
|
||||||
{
|
{
|
||||||
level = l;
|
level = lvl;
|
||||||
os << "[";
|
os << "[";
|
||||||
switch (level)
|
switch (level)
|
||||||
{
|
{
|
||||||
|
|||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef STD_HASH_EXTENSIONS_H
|
#ifndef STD_HASH_HPP
|
||||||
#define STD_HASH_EXTENSIONS_H
|
#define STD_HASH_HPP
|
||||||
|
|
||||||
#include <functional>
|
#include <functional>
|
||||||
|
|
||||||
@@ -74,4 +74,4 @@ template <typename T1, typename T2> struct hash<std::pair<T1, T2>>
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif // STD_HASH_EXTENSIONS_H
|
#endif // STD_HASH_HPP
|
||||||
@@ -0,0 +1,80 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef TIMING_UTIL_HPP
|
||||||
|
#define TIMING_UTIL_HPP
|
||||||
|
|
||||||
|
#include <atomic>
|
||||||
|
#include <chrono>
|
||||||
|
#include <cstdint>
|
||||||
|
#include <mutex>
|
||||||
|
#include <unordered_map>
|
||||||
|
|
||||||
|
struct GlobalTimer
|
||||||
|
{
|
||||||
|
GlobalTimer() : time(0) {}
|
||||||
|
std::atomic<uint64_t> time;
|
||||||
|
};
|
||||||
|
|
||||||
|
class GlobalTimerFactory
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
static GlobalTimerFactory& get()
|
||||||
|
{
|
||||||
|
static GlobalTimerFactory instance;
|
||||||
|
return instance;
|
||||||
|
}
|
||||||
|
|
||||||
|
GlobalTimer& getGlobalTimer(const std::string& name)
|
||||||
|
{
|
||||||
|
std::lock_guard<std::mutex> lock(map_mutex);
|
||||||
|
return timer_map[name];
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
std::mutex map_mutex;
|
||||||
|
std::unordered_map<std::string, GlobalTimer> timer_map;
|
||||||
|
};
|
||||||
|
|
||||||
|
#define GLOBAL_TIMER_AQUIRE(_X) auto& _X##_global_timer = GlobalTimerFactory::get().getGlobalTimer(#_X)
|
||||||
|
#define GLOBAL_TIMER_RESET(_X) _X##_global_timer.time = 0
|
||||||
|
#define GLOBAL_TIMER_START(_X) TIMER_START(_X)
|
||||||
|
#define GLOBAL_TIMER_STOP(_X) TIMER_STOP(_X); _X##_global_timer.time += TIMER_NSEC(_X)
|
||||||
|
#define GLOBAL_TIMER_NSEC(_X) static_cast<double>(_X##_global_timer.time)
|
||||||
|
#define GLOBAL_TIMER_USEC(_X) (_X##_global_timer.time / 1000.0)
|
||||||
|
#define GLOBAL_TIMER_MSEC(_X) (_X##_global_timer.time / 1000.0 / 1000.0)
|
||||||
|
#define GLOBAL_TIMER_SEC(_X) (_X##_global_timer.time / 1000.0 / 1000.0 / 1000.0)
|
||||||
|
|
||||||
|
#define TIMER_START(_X) auto _X##_start = std::chrono::steady_clock::now(), _X##_stop = _X##_start
|
||||||
|
#define TIMER_STOP(_X) _X##_stop = std::chrono::steady_clock::now()
|
||||||
|
#define TIMER_NSEC(_X) std::chrono::duration_cast<std::chrono::nanoseconds>(_X##_stop - _X##_start).count()
|
||||||
|
#define TIMER_USEC(_X) std::chrono::duration_cast<std::chrono::microseconds>(_X##_stop - _X##_start).count()
|
||||||
|
#define TIMER_MSEC(_X) (0.000001*std::chrono::duration_cast<std::chrono::nanoseconds>(_X##_stop - _X##_start).count())
|
||||||
|
#define TIMER_SEC(_X) (0.000001*std::chrono::duration_cast<std::chrono::microseconds>(_X##_stop - _X##_start).count())
|
||||||
|
#define TIMER_MIN(_X) std::chrono::duration_cast<std::chrono::minutes>(_X##_stop - _X##_start).count()
|
||||||
|
|
||||||
|
#endif // TIMING_UTIL_HPP
|
||||||
@@ -0,0 +1,140 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef XML_RENDERER_HPP
|
||||||
|
#define XML_RENDERER_HPP
|
||||||
|
|
||||||
|
#include "../data_structures/json_container.hpp"
|
||||||
|
#include "cast.hpp"
|
||||||
|
|
||||||
|
namespace JSON {
|
||||||
|
|
||||||
|
struct XMLToArrayRenderer : mapbox::util::static_visitor<>
|
||||||
|
{
|
||||||
|
explicit XMLToArrayRenderer(std::vector<char> &_out) : out(_out) {}
|
||||||
|
|
||||||
|
void operator()(const String &string) const
|
||||||
|
{
|
||||||
|
out.push_back('\"');
|
||||||
|
out.insert(out.end(), string.value.begin(), string.value.end());
|
||||||
|
out.push_back('\"');
|
||||||
|
}
|
||||||
|
|
||||||
|
void operator()(const Number &number) const
|
||||||
|
{
|
||||||
|
const std::string number_string = cast::double_fixed_to_string(number.value);
|
||||||
|
out.insert(out.end(), number_string.begin(), number_string.end());
|
||||||
|
}
|
||||||
|
|
||||||
|
void operator()(const Object &object) const
|
||||||
|
{
|
||||||
|
auto iterator = object.values.begin();
|
||||||
|
while (iterator != object.values.end())
|
||||||
|
{
|
||||||
|
if (iterator->first.at(0) != '_')
|
||||||
|
{
|
||||||
|
out.push_back('<');
|
||||||
|
out.insert(out.end(), (*iterator).first.begin(), (*iterator).first.end());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
out.push_back(' ');
|
||||||
|
out.insert(out.end(), ++(*iterator).first.begin(), (*iterator).first.end());
|
||||||
|
out.push_back('=');
|
||||||
|
|
||||||
|
}
|
||||||
|
mapbox::util::apply_visitor(XMLToArrayRenderer(out), (*iterator).second);
|
||||||
|
if (iterator->first.at(0) != '_')
|
||||||
|
{
|
||||||
|
out.push_back('/');
|
||||||
|
out.push_back('>');
|
||||||
|
}
|
||||||
|
++iterator;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void operator()(const Array &array) const
|
||||||
|
{
|
||||||
|
std::vector<Value>::const_iterator iterator;
|
||||||
|
iterator = array.values.begin();
|
||||||
|
while (iterator != array.values.end())
|
||||||
|
{
|
||||||
|
mapbox::util::apply_visitor(XMLToArrayRenderer(out), *iterator);
|
||||||
|
++iterator;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
void operator()(const True &) const
|
||||||
|
{
|
||||||
|
const std::string temp("true");
|
||||||
|
out.insert(out.end(), temp.begin(), temp.end());
|
||||||
|
}
|
||||||
|
|
||||||
|
void operator()(const False &) const
|
||||||
|
{
|
||||||
|
const std::string temp("false");
|
||||||
|
out.insert(out.end(), temp.begin(), temp.end());
|
||||||
|
}
|
||||||
|
|
||||||
|
void operator()(const Null &) const
|
||||||
|
{
|
||||||
|
const std::string temp("null");
|
||||||
|
out.insert(out.end(), temp.begin(), temp.end());
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
std::vector<char> &out;
|
||||||
|
};
|
||||||
|
|
||||||
|
template<class JSONObject>
|
||||||
|
inline void xml_render(std::vector<char> &out, const JSONObject &object)
|
||||||
|
{
|
||||||
|
Value value = object;
|
||||||
|
mapbox::util::apply_visitor(XMLToArrayRenderer(out), value);
|
||||||
|
}
|
||||||
|
|
||||||
|
template<class JSONObject>
|
||||||
|
inline void gpx_render(std::vector<char> &out, const JSONObject &object)
|
||||||
|
{
|
||||||
|
// add header
|
||||||
|
|
||||||
|
const std::string header {"<?xml version=\"1.0\" encoding=\"UTF-8\"?><gpx creator=\"OSRM Routing Engine\""
|
||||||
|
" version=\"1.1\" xmlns=\"http://www.topografix.com/GPX/1/1\" xmlns:xsi=\"http:"
|
||||||
|
"//www.w3.org/2001/XMLSchema-instance\" xsi:schemaLocation=\"http://www.topogr"
|
||||||
|
"afix.com/GPX/1/1 gpx.xsd\"><metadata><copyright author=\"Project OSRM\"><lice"
|
||||||
|
"nse>Data (c) OpenStreetMap contributors (ODbL)</license></copyright></metadat"
|
||||||
|
"a><rte>"};
|
||||||
|
out.insert(out.end(), header.begin(), header.end());
|
||||||
|
|
||||||
|
xml_render(out, object);
|
||||||
|
|
||||||
|
const std::string footer {"</rte></gpx>"};
|
||||||
|
out.insert(out.end(), footer.begin(), footer.end());
|
||||||
|
}
|
||||||
|
} // namespace JSON
|
||||||
|
|
||||||
|
#endif // XML_RENDERER_HPP
|
||||||
@@ -1,8 +1,35 @@
|
|||||||
#ifndef BFS_COMPONENT_EXPLORER_H_
|
/*
|
||||||
#define BFS_COMPONENT_EXPLORER_H_
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef BFS_COMPONENTS_HPP_
|
||||||
|
#define BFS_COMPONENTS_HPP_
|
||||||
|
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
#include "../DataStructures/RestrictionMap.h"
|
#include "../data_structures/restriction_map.hpp"
|
||||||
|
|
||||||
#include <queue>
|
#include <queue>
|
||||||
#include <unordered_set>
|
#include <unordered_set>
|
||||||
@@ -144,4 +171,4 @@ template <typename GraphT> class BFSComponentExplorer
|
|||||||
const std::unordered_set<NodeID> &m_barrier_nodes;
|
const std::unordered_set<NodeID> &m_barrier_nodes;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // BFS_COMPONENT_EXPLORER_H_
|
#endif // BFS_COMPONENTS_HPP_
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,10 +25,10 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "DouglasPeucker.h"
|
#include "douglas_peucker.hpp"
|
||||||
|
|
||||||
#include "../DataStructures/Range.h"
|
#include "../data_structures/segment_information.hpp"
|
||||||
#include "../DataStructures/SegmentInformation.h"
|
#include "../Util/integer_range.hpp"
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
#include <osrm/Coordinate.h>
|
||||||
|
|
||||||
@@ -38,7 +38,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
|
|
||||||
namespace {
|
namespace
|
||||||
|
{
|
||||||
struct CoordinatePairCalculator
|
struct CoordinatePairCalculator
|
||||||
{
|
{
|
||||||
CoordinatePairCalculator() = delete;
|
CoordinatePairCalculator() = delete;
|
||||||
@@ -82,61 +83,40 @@ struct CoordinatePairCalculator
|
|||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
DouglasPeucker::DouglasPeucker()
|
|
||||||
: douglas_peucker_thresholds({512440, // z0
|
|
||||||
256720, // z1
|
|
||||||
122560, // z2
|
|
||||||
56780, // z3
|
|
||||||
28800, // z4
|
|
||||||
14400, // z5
|
|
||||||
7200, // z6
|
|
||||||
3200, // z7
|
|
||||||
2400, // z8
|
|
||||||
1000, // z9
|
|
||||||
600, // z10
|
|
||||||
120, // z11
|
|
||||||
60, // z12
|
|
||||||
45, // z13
|
|
||||||
36, // z14
|
|
||||||
20, // z15
|
|
||||||
8, // z16
|
|
||||||
6, // z17
|
|
||||||
4 // z18
|
|
||||||
})
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
void DouglasPeucker::Run(std::vector<SegmentInformation> &input_geometry, const unsigned zoom_level)
|
void DouglasPeucker::Run(std::vector<SegmentInformation> &input_geometry, const unsigned zoom_level)
|
||||||
{
|
{
|
||||||
// check if input data is invalid
|
Run(std::begin(input_geometry), std::end(input_geometry), zoom_level);
|
||||||
BOOST_ASSERT_MSG(!input_geometry.empty(), "geometry invalid");
|
}
|
||||||
|
|
||||||
if (input_geometry.size() < 2)
|
void DouglasPeucker::Run(RandomAccessIt begin, RandomAccessIt end, const unsigned zoom_level)
|
||||||
|
{
|
||||||
|
unsigned size = std::distance(begin, end);
|
||||||
|
if (size < 2)
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
input_geometry.front().necessary = true;
|
begin->necessary = true;
|
||||||
input_geometry.back().necessary = true;
|
std::prev(end)->necessary = true;
|
||||||
|
|
||||||
{
|
{
|
||||||
BOOST_ASSERT_MSG(zoom_level < 19, "unsupported zoom level");
|
BOOST_ASSERT_MSG(zoom_level < DOUGLAS_PEUCKER_THRESHOLDS.size(), "unsupported zoom level");
|
||||||
unsigned left_border = 0;
|
RandomAccessIt left_border = begin;
|
||||||
unsigned right_border = 1;
|
RandomAccessIt right_border = std::next(begin);
|
||||||
// Sweep over array and identify those ranges that need to be checked
|
// Sweep over array and identify those ranges that need to be checked
|
||||||
do
|
do
|
||||||
{
|
{
|
||||||
// traverse list until new border element found
|
// traverse list until new border element found
|
||||||
if (input_geometry[right_border].necessary)
|
if (right_border->necessary)
|
||||||
{
|
{
|
||||||
// sanity checks
|
// sanity checks
|
||||||
BOOST_ASSERT(input_geometry[left_border].necessary);
|
BOOST_ASSERT(left_border->necessary);
|
||||||
BOOST_ASSERT(input_geometry[right_border].necessary);
|
BOOST_ASSERT(right_border->necessary);
|
||||||
recursion_stack.emplace(left_border, right_border);
|
recursion_stack.emplace(left_border, right_border);
|
||||||
left_border = right_border;
|
left_border = right_border;
|
||||||
}
|
}
|
||||||
++right_border;
|
++right_border;
|
||||||
} while (right_border < input_geometry.size());
|
} while (right_border != end);
|
||||||
}
|
}
|
||||||
|
|
||||||
// mark locations as 'necessary' by divide-and-conquer
|
// mark locations as 'necessary' by divide-and-conquer
|
||||||
@@ -146,40 +126,40 @@ void DouglasPeucker::Run(std::vector<SegmentInformation> &input_geometry, const
|
|||||||
const GeometryRange pair = recursion_stack.top();
|
const GeometryRange pair = recursion_stack.top();
|
||||||
recursion_stack.pop();
|
recursion_stack.pop();
|
||||||
// sanity checks
|
// sanity checks
|
||||||
BOOST_ASSERT_MSG(input_geometry[pair.first].necessary, "left border mus be necessary");
|
BOOST_ASSERT_MSG(pair.first->necessary, "left border must be necessary");
|
||||||
BOOST_ASSERT_MSG(input_geometry[pair.second].necessary, "right border must be necessary");
|
BOOST_ASSERT_MSG(pair.second->necessary, "right border must be necessary");
|
||||||
BOOST_ASSERT_MSG(pair.second < input_geometry.size(), "right border outside of geometry");
|
BOOST_ASSERT_MSG(std::distance(pair.second, end) > 0, "right border outside of geometry");
|
||||||
BOOST_ASSERT_MSG(pair.first < pair.second, "left border on the wrong side");
|
BOOST_ASSERT_MSG(std::distance(pair.first, pair.second) >= 0,
|
||||||
|
"left border on the wrong side");
|
||||||
|
|
||||||
int max_int_distance = 0;
|
int max_int_distance = 0;
|
||||||
unsigned farthest_entry_index = pair.second;
|
auto farthest_entry_it = pair.second;
|
||||||
const CoordinatePairCalculator dist_calc(input_geometry[pair.first].location,
|
const CoordinatePairCalculator dist_calc(pair.first->location, pair.second->location);
|
||||||
input_geometry[pair.second].location);
|
|
||||||
|
|
||||||
// sweep over range to find the maximum
|
// sweep over range to find the maximum
|
||||||
for (const auto i : osrm::irange(pair.first + 1, pair.second))
|
for (auto it = std::next(pair.first); it != pair.second; ++it)
|
||||||
{
|
{
|
||||||
const int distance = dist_calc(input_geometry[i].location);
|
const int distance = dist_calc(it->location);
|
||||||
// found new feasible maximum?
|
// found new feasible maximum?
|
||||||
if (distance > max_int_distance && distance > douglas_peucker_thresholds[zoom_level])
|
if (distance > max_int_distance && distance > DOUGLAS_PEUCKER_THRESHOLDS[zoom_level])
|
||||||
{
|
{
|
||||||
farthest_entry_index = i;
|
farthest_entry_it = it;
|
||||||
max_int_distance = distance;
|
max_int_distance = distance;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// check if maximum violates a zoom level dependent threshold
|
// check if maximum violates a zoom level dependent threshold
|
||||||
if (max_int_distance > douglas_peucker_thresholds[zoom_level])
|
if (max_int_distance > DOUGLAS_PEUCKER_THRESHOLDS[zoom_level])
|
||||||
{
|
{
|
||||||
// mark idx as necessary
|
// mark idx as necessary
|
||||||
input_geometry[farthest_entry_index].necessary = true;
|
farthest_entry_it->necessary = true;
|
||||||
if (1 < (farthest_entry_index - pair.first))
|
if (1 < std::distance(pair.first, farthest_entry_it))
|
||||||
{
|
{
|
||||||
recursion_stack.emplace(pair.first, farthest_entry_index);
|
recursion_stack.emplace(pair.first, farthest_entry_it);
|
||||||
}
|
}
|
||||||
if (1 < (pair.second - farthest_entry_index))
|
if (1 < std::distance(farthest_entry_it, pair.second))
|
||||||
{
|
{
|
||||||
recursion_stack.emplace(farthest_entry_index, pair.second);
|
recursion_stack.emplace(farthest_entry_it, pair.second);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@@ -25,12 +25,12 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef DOUGLASPEUCKER_H_
|
#ifndef DOUGLAS_PEUCKER_HPP_
|
||||||
#define DOUGLASPEUCKER_H_
|
#define DOUGLAS_PEUCKER_HPP_
|
||||||
|
|
||||||
#include <stack>
|
#include <stack>
|
||||||
#include <utility>
|
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
#include <array>
|
||||||
|
|
||||||
/* This class object computes the bitvector of indicating generalized input
|
/* This class object computes the bitvector of indicating generalized input
|
||||||
* points according to the (Ramer-)Douglas-Peucker algorithm.
|
* points according to the (Ramer-)Douglas-Peucker algorithm.
|
||||||
@@ -41,18 +41,40 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
struct SegmentInformation;
|
struct SegmentInformation;
|
||||||
|
|
||||||
|
static const std::array<int, 19> DOUGLAS_PEUCKER_THRESHOLDS {{
|
||||||
|
512440, // z0
|
||||||
|
256720, // z1
|
||||||
|
122560, // z2
|
||||||
|
56780, // z3
|
||||||
|
28800, // z4
|
||||||
|
14400, // z5
|
||||||
|
7200, // z6
|
||||||
|
3200, // z7
|
||||||
|
2400, // z8
|
||||||
|
1000, // z9
|
||||||
|
600, // z10
|
||||||
|
120, // z11
|
||||||
|
60, // z12
|
||||||
|
45, // z13
|
||||||
|
36, // z14
|
||||||
|
20, // z15
|
||||||
|
8, // z16
|
||||||
|
6, // z17
|
||||||
|
4 // z18
|
||||||
|
}};
|
||||||
|
|
||||||
class DouglasPeucker
|
class DouglasPeucker
|
||||||
{
|
{
|
||||||
private:
|
public:
|
||||||
std::vector<int> douglas_peucker_thresholds;
|
using RandomAccessIt = std::vector<SegmentInformation>::iterator;
|
||||||
|
|
||||||
using GeometryRange = std::pair<unsigned, unsigned>;
|
using GeometryRange = std::pair<RandomAccessIt, RandomAccessIt>;
|
||||||
// Stack to simulate the recursion
|
// Stack to simulate the recursion
|
||||||
std::stack<GeometryRange> recursion_stack;
|
std::stack<GeometryRange> recursion_stack;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
DouglasPeucker();
|
void Run(RandomAccessIt begin, RandomAccessIt end, const unsigned zoom_level);
|
||||||
void Run(std::vector<SegmentInformation> &input_geometry, const unsigned zoom_level);
|
void Run(std::vector<SegmentInformation> &input_geometry, const unsigned zoom_level);
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* DOUGLASPEUCKER_H_ */
|
#endif /* DOUGLAS_PEUCKER_HPP_ */
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef OBJECT_TO_BASE64_H_
|
#ifndef OBJECT_ENCODER_HPP
|
||||||
#define OBJECT_TO_BASE64_H_
|
#define OBJECT_ENCODER_HPP
|
||||||
|
|
||||||
#include "../Util/StringUtil.h"
|
#include "../Util/StringUtil.h"
|
||||||
|
|
||||||
@@ -91,4 +91,4 @@ struct ObjectEncoder
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* OBJECT_TO_BASE64_H_ */
|
#endif /* OBJECT_ENCODER_HPP */
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,16 +25,16 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "PolylineCompressor.h"
|
#include "polyline_compressor.hpp"
|
||||||
#include "../DataStructures/SegmentInformation.h"
|
#include "../data_structures/segment_information.hpp"
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
#include <osrm/Coordinate.h>
|
||||||
|
|
||||||
void PolylineCompressor::encodeVectorSignedNumber(std::vector<int> &numbers,
|
std::string PolylineCompressor::encode_vector(std::vector<int> &numbers) const
|
||||||
std::string &output) const
|
|
||||||
{
|
{
|
||||||
const unsigned end = static_cast<unsigned>(numbers.size());
|
std::string output;
|
||||||
for (unsigned i = 0; i < end; ++i)
|
const auto end = numbers.size();
|
||||||
|
for (std::size_t i = 0; i < end; ++i)
|
||||||
{
|
{
|
||||||
numbers[i] <<= 1;
|
numbers[i] <<= 1;
|
||||||
if (numbers[i] < 0)
|
if (numbers[i] < 0)
|
||||||
@@ -44,12 +44,14 @@ void PolylineCompressor::encodeVectorSignedNumber(std::vector<int> &numbers,
|
|||||||
}
|
}
|
||||||
for (const int number : numbers)
|
for (const int number : numbers)
|
||||||
{
|
{
|
||||||
encodeNumber(number, output);
|
output += encode_number(number);
|
||||||
}
|
}
|
||||||
|
return output;
|
||||||
}
|
}
|
||||||
|
|
||||||
void PolylineCompressor::encodeNumber(int number_to_encode, std::string &output) const
|
std::string PolylineCompressor::encode_number(int number_to_encode) const
|
||||||
{
|
{
|
||||||
|
std::string output;
|
||||||
while (number_to_encode >= 0x20)
|
while (number_to_encode >= 0x20)
|
||||||
{
|
{
|
||||||
const int next_value = (0x20 | (number_to_encode & 0x1f)) + 63;
|
const int next_value = (0x20 | (number_to_encode & 0x1f)) + 63;
|
||||||
@@ -67,46 +69,30 @@ void PolylineCompressor::encodeNumber(int number_to_encode, std::string &output)
|
|||||||
{
|
{
|
||||||
output += static_cast<char>(number_to_encode);
|
output += static_cast<char>(number_to_encode);
|
||||||
}
|
}
|
||||||
|
return output;
|
||||||
}
|
}
|
||||||
|
|
||||||
JSON::String
|
std::string
|
||||||
PolylineCompressor::printEncodedString(const std::vector<SegmentInformation> &polyline) const
|
PolylineCompressor::get_encoded_string(const std::vector<SegmentInformation> &polyline) const
|
||||||
{
|
{
|
||||||
std::string output;
|
if (polyline.empty())
|
||||||
std::vector<int> delta_numbers;
|
|
||||||
if (!polyline.empty())
|
|
||||||
{
|
{
|
||||||
FixedPointCoordinate last_coordinate = {0, 0};
|
return {};
|
||||||
|
}
|
||||||
|
|
||||||
|
std::vector<int> delta_numbers;
|
||||||
|
delta_numbers.reserve((polyline.size() - 1) * 2);
|
||||||
|
FixedPointCoordinate previous_coordinate = {0, 0};
|
||||||
for (const auto &segment : polyline)
|
for (const auto &segment : polyline)
|
||||||
{
|
{
|
||||||
if (segment.necessary)
|
if (segment.necessary)
|
||||||
{
|
{
|
||||||
const int lat_diff = segment.location.lat - last_coordinate.lat;
|
const int lat_diff = segment.location.lat - previous_coordinate.lat;
|
||||||
const int lon_diff = segment.location.lon - last_coordinate.lon;
|
const int lon_diff = segment.location.lon - previous_coordinate.lon;
|
||||||
delta_numbers.emplace_back(lat_diff);
|
delta_numbers.emplace_back(lat_diff);
|
||||||
delta_numbers.emplace_back(lon_diff);
|
delta_numbers.emplace_back(lon_diff);
|
||||||
last_coordinate = segment.location;
|
previous_coordinate = segment.location;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
encodeVectorSignedNumber(delta_numbers, output);
|
return encode_vector(delta_numbers);
|
||||||
}
|
|
||||||
JSON::String return_value(output);
|
|
||||||
return return_value;
|
|
||||||
}
|
|
||||||
|
|
||||||
JSON::Array
|
|
||||||
PolylineCompressor::printUnencodedString(const std::vector<SegmentInformation> &polyline) const
|
|
||||||
{
|
|
||||||
JSON::Array json_geometry_array;
|
|
||||||
for (const auto &segment : polyline)
|
|
||||||
{
|
|
||||||
if (segment.necessary)
|
|
||||||
{
|
|
||||||
JSON::Array json_coordinate;
|
|
||||||
json_coordinate.values.push_back(segment.location.lat / COORDINATE_PRECISION);
|
|
||||||
json_coordinate.values.push_back(segment.location.lon / COORDINATE_PRECISION);
|
|
||||||
json_geometry_array.values.push_back(json_coordinate);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
return json_geometry_array;
|
|
||||||
}
|
}
|
||||||
@@ -30,22 +30,18 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
struct SegmentInformation;
|
struct SegmentInformation;
|
||||||
|
|
||||||
#include "../DataStructures/JSONContainer.h"
|
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
class PolylineCompressor
|
class PolylineCompressor
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
void encodeVectorSignedNumber(std::vector<int> &numbers, std::string &output) const;
|
std::string encode_vector(std::vector<int> &numbers) const;
|
||||||
|
|
||||||
void encodeNumber(int number_to_encode, std::string &output) const;
|
std::string encode_number(const int number_to_encode) const;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
JSON::String printEncodedString(const std::vector<SegmentInformation> &polyline) const;
|
std::string get_encoded_string(const std::vector<SegmentInformation> &polyline) const;
|
||||||
|
|
||||||
JSON::Array printUnencodedString(const std::vector<SegmentInformation> &polyline) const;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* POLYLINECOMPRESSOR_H_ */
|
#endif /* POLYLINECOMPRESSOR_H_ */
|
||||||
@@ -0,0 +1,56 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "polyline_formatter.hpp"
|
||||||
|
|
||||||
|
#include "polyline_compressor.hpp"
|
||||||
|
#include "../data_structures/segment_information.hpp"
|
||||||
|
|
||||||
|
#include <osrm/Coordinate.h>
|
||||||
|
|
||||||
|
JSON::String
|
||||||
|
PolylineFormatter::printEncodedString(const std::vector<SegmentInformation> &polyline) const
|
||||||
|
{
|
||||||
|
return JSON::String(PolylineCompressor().get_encoded_string(polyline));
|
||||||
|
}
|
||||||
|
|
||||||
|
JSON::Array
|
||||||
|
PolylineFormatter::printUnencodedString(const std::vector<SegmentInformation> &polyline) const
|
||||||
|
{
|
||||||
|
JSON::Array json_geometry_array;
|
||||||
|
for (const auto &segment : polyline)
|
||||||
|
{
|
||||||
|
if (segment.necessary)
|
||||||
|
{
|
||||||
|
JSON::Array json_coordinate;
|
||||||
|
json_coordinate.values.push_back(segment.location.lat / COORDINATE_PRECISION);
|
||||||
|
json_coordinate.values.push_back(segment.location.lon / COORDINATE_PRECISION);
|
||||||
|
json_geometry_array.values.push_back(json_coordinate);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return json_geometry_array;
|
||||||
|
}
|
||||||
@@ -0,0 +1,45 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef POLYLINE_FORMATTER_HPP
|
||||||
|
#define POLYLINE_FORMATTER_HPP
|
||||||
|
|
||||||
|
struct SegmentInformation;
|
||||||
|
|
||||||
|
#include "../data_structures/json_container.hpp"
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
|
struct PolylineFormatter
|
||||||
|
{
|
||||||
|
JSON::String printEncodedString(const std::vector<SegmentInformation> &polyline) const;
|
||||||
|
|
||||||
|
JSON::Array printUnencodedString(const std::vector<SegmentInformation> &polyline) const;
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif /* POLYLINE_FORMATTER_HPP */
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,38 +25,29 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef STRONGLYCONNECTEDCOMPONENTS_H_
|
#ifndef TINY_COMPONENTS_HPP
|
||||||
#define STRONGLYCONNECTEDCOMPONENTS_H_
|
#define TINY_COMPONENTS_HPP
|
||||||
|
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
#include "../DataStructures/DeallocatingVector.h"
|
#include "../data_structures/deallocating_vector.hpp"
|
||||||
#include "../DataStructures/DynamicGraph.h"
|
#include "../data_structures/import_edge.hpp"
|
||||||
#include "../DataStructures/ImportEdge.h"
|
#include "../data_structures/query_node.hpp"
|
||||||
#include "../DataStructures/QueryNode.h"
|
#include "../data_structures/percent.hpp"
|
||||||
#include "../DataStructures/Percent.h"
|
#include "../data_structures/restriction.hpp"
|
||||||
#include "../DataStructures/Range.h"
|
#include "../data_structures/turn_instructions.hpp"
|
||||||
#include "../DataStructures/Restriction.h"
|
|
||||||
#include "../DataStructures/TurnInstructions.h"
|
|
||||||
|
|
||||||
|
#include "../Util/integer_range.hpp"
|
||||||
#include "../Util/OSRMException.h"
|
#include "../Util/OSRMException.h"
|
||||||
#include "../Util/simple_logger.hpp"
|
#include "../Util/simple_logger.hpp"
|
||||||
#include "../Util/StdHashExtensions.h"
|
#include "../Util/std_hash.hpp"
|
||||||
#include "../Util/TimingUtil.h"
|
#include "../Util/timing_util.hpp"
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
#include <osrm/Coordinate.h>
|
||||||
|
|
||||||
#include <boost/assert.hpp>
|
#include <boost/assert.hpp>
|
||||||
#include <boost/filesystem.hpp>
|
|
||||||
|
|
||||||
#include <tbb/parallel_sort.h>
|
#include <tbb/parallel_sort.h>
|
||||||
|
|
||||||
#ifdef __APPLE__
|
|
||||||
#include <gdal.h>
|
|
||||||
#include <ogrsf_frmts.h>
|
|
||||||
#else
|
|
||||||
#include <gdal/gdal.h>
|
|
||||||
#include <gdal/ogrsf_frmts.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include <cstdint>
|
#include <cstdint>
|
||||||
|
|
||||||
@@ -66,9 +57,16 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
#include <unordered_set>
|
#include <unordered_set>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
|
template <typename GraphT>
|
||||||
class TarjanSCC
|
class TarjanSCC
|
||||||
{
|
{
|
||||||
private:
|
struct TarjanStackFrame
|
||||||
|
{
|
||||||
|
explicit TarjanStackFrame(NodeID v, NodeID parent) : v(v), parent(parent) {}
|
||||||
|
NodeID v;
|
||||||
|
NodeID parent;
|
||||||
|
};
|
||||||
|
|
||||||
struct TarjanNode
|
struct TarjanNode
|
||||||
{
|
{
|
||||||
TarjanNode() : index(SPECIAL_NODEID), low_link(SPECIAL_NODEID), on_stack(false) {}
|
TarjanNode() : index(SPECIAL_NODEID), low_link(SPECIAL_NODEID), on_stack(false) {}
|
||||||
@@ -77,50 +75,33 @@ class TarjanSCC
|
|||||||
bool on_stack;
|
bool on_stack;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct TarjanEdgeData
|
|
||||||
{
|
|
||||||
TarjanEdgeData() : distance(INVALID_EDGE_WEIGHT), name_id(INVALID_NAMEID) {}
|
|
||||||
TarjanEdgeData(int distance, unsigned name_id) : distance(distance), name_id(name_id) {}
|
|
||||||
int distance;
|
|
||||||
unsigned name_id;
|
|
||||||
};
|
|
||||||
|
|
||||||
struct TarjanStackFrame
|
|
||||||
{
|
|
||||||
explicit TarjanStackFrame(NodeID v, NodeID parent) : v(v), parent(parent) {}
|
|
||||||
NodeID v;
|
|
||||||
NodeID parent;
|
|
||||||
};
|
|
||||||
|
|
||||||
using TarjanDynamicGraph = DynamicGraph<TarjanEdgeData>;
|
|
||||||
using TarjanEdge = TarjanDynamicGraph::InputEdge;
|
|
||||||
using RestrictionSource = std::pair<NodeID, NodeID>;
|
using RestrictionSource = std::pair<NodeID, NodeID>;
|
||||||
using RestrictionTarget = std::pair<NodeID, bool>;
|
using RestrictionTarget = std::pair<NodeID, bool>;
|
||||||
using EmanatingRestrictionsVector = std::vector<RestrictionTarget>;
|
using EmanatingRestrictionsVector = std::vector<RestrictionTarget>;
|
||||||
using RestrictionMap = std::unordered_map<RestrictionSource, unsigned>;
|
using RestrictionMap = std::unordered_map<RestrictionSource, unsigned>;
|
||||||
|
|
||||||
std::vector<NodeInfo> m_coordinate_list;
|
|
||||||
std::vector<EmanatingRestrictionsVector> m_restriction_bucket_list;
|
std::vector<EmanatingRestrictionsVector> m_restriction_bucket_list;
|
||||||
std::shared_ptr<TarjanDynamicGraph> m_node_based_graph;
|
std::vector<unsigned> components_index;
|
||||||
|
std::vector<NodeID> component_size_vector;
|
||||||
|
std::shared_ptr<GraphT> m_node_based_graph;
|
||||||
std::unordered_set<NodeID> barrier_node_list;
|
std::unordered_set<NodeID> barrier_node_list;
|
||||||
std::unordered_set<NodeID> traffic_light_list;
|
unsigned size_one_counter;
|
||||||
unsigned m_restriction_counter;
|
|
||||||
RestrictionMap m_restriction_map;
|
RestrictionMap m_restriction_map;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
TarjanSCC(int number_of_nodes,
|
TarjanSCC(std::shared_ptr<GraphT> graph,
|
||||||
std::vector<NodeBasedEdge> &input_edges,
|
|
||||||
std::vector<NodeID> &bn,
|
std::vector<NodeID> &bn,
|
||||||
std::vector<NodeID> &tl,
|
std::vector<TurnRestriction> &irs)
|
||||||
std::vector<TurnRestriction> &irs,
|
: components_index(graph->GetNumberOfNodes(), SPECIAL_NODEID),
|
||||||
std::vector<NodeInfo> &nI)
|
m_node_based_graph(graph),
|
||||||
: m_coordinate_list(nI), m_restriction_counter(irs.size())
|
size_one_counter(0)
|
||||||
{
|
{
|
||||||
|
|
||||||
TIMER_START(SCC_LOAD);
|
TIMER_START(SCC_LOAD);
|
||||||
for (const TurnRestriction &restriction : irs)
|
for (const TurnRestriction &restriction : irs)
|
||||||
{
|
{
|
||||||
std::pair<NodeID, NodeID> restriction_source = {restriction.fromNode,
|
std::pair<NodeID, NodeID> restriction_source = {restriction.from.node,
|
||||||
restriction.viaNode};
|
restriction.via.node};
|
||||||
unsigned index = 0;
|
unsigned index = 0;
|
||||||
const auto restriction_iterator = m_restriction_map.find(restriction_source);
|
const auto restriction_iterator = m_restriction_map.find(restriction_source);
|
||||||
if (restriction_iterator == m_restriction_map.end())
|
if (restriction_iterator == m_restriction_map.end())
|
||||||
@@ -137,7 +118,7 @@ class TarjanSCC
|
|||||||
{
|
{
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
else if (restriction.flags.isOnly)
|
else if (restriction.flags.is_only)
|
||||||
{
|
{
|
||||||
// We are going to insert an is_only_*-restriction. There can be only one.
|
// We are going to insert an is_only_*-restriction. There can be only one.
|
||||||
m_restriction_bucket_list.at(index).clear();
|
m_restriction_bucket_list.at(index).clear();
|
||||||
@@ -145,95 +126,23 @@ class TarjanSCC
|
|||||||
}
|
}
|
||||||
|
|
||||||
m_restriction_bucket_list.at(index)
|
m_restriction_bucket_list.at(index)
|
||||||
.emplace_back(restriction.toNode, restriction.flags.isOnly);
|
.emplace_back(restriction.to.node, restriction.flags.is_only);
|
||||||
}
|
}
|
||||||
|
|
||||||
barrier_node_list.insert(bn.begin(), bn.end());
|
barrier_node_list.insert(bn.begin(), bn.end());
|
||||||
traffic_light_list.insert(tl.begin(), tl.end());
|
|
||||||
|
|
||||||
DeallocatingVector<TarjanEdge> edge_list;
|
|
||||||
for (const NodeBasedEdge &input_edge : input_edges)
|
|
||||||
{
|
|
||||||
if (input_edge.source == input_edge.target)
|
|
||||||
{
|
|
||||||
continue;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (input_edge.forward)
|
|
||||||
{
|
|
||||||
edge_list.emplace_back(input_edge.source,
|
|
||||||
input_edge.target,
|
|
||||||
(std::max)((int)input_edge.weight, 1),
|
|
||||||
input_edge.name_id);
|
|
||||||
}
|
|
||||||
if (input_edge.backward)
|
|
||||||
{
|
|
||||||
edge_list.emplace_back(input_edge.target,
|
|
||||||
input_edge.source,
|
|
||||||
(std::max)((int)input_edge.weight, 1),
|
|
||||||
input_edge.name_id);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
input_edges.clear();
|
|
||||||
input_edges.shrink_to_fit();
|
|
||||||
BOOST_ASSERT_MSG(0 == input_edges.size() && 0 == input_edges.capacity(),
|
|
||||||
"input edge vector not properly deallocated");
|
|
||||||
|
|
||||||
tbb::parallel_sort(edge_list.begin(), edge_list.end());
|
|
||||||
m_node_based_graph = std::make_shared<TarjanDynamicGraph>(number_of_nodes, edge_list);
|
|
||||||
TIMER_STOP(SCC_LOAD);
|
TIMER_STOP(SCC_LOAD);
|
||||||
SimpleLogger().Write() << "Loading data into SCC took " << TIMER_MSEC(SCC_LOAD)/1000. << "s";
|
SimpleLogger().Write() << "Loading data into SCC took " << TIMER_MSEC(SCC_LOAD)/1000. << "s";
|
||||||
}
|
}
|
||||||
|
|
||||||
~TarjanSCC() { m_node_based_graph.reset(); }
|
|
||||||
|
|
||||||
void Run()
|
void Run()
|
||||||
{
|
{
|
||||||
TIMER_START(SCC_RUN_SETUP);
|
|
||||||
// remove files from previous run if exist
|
|
||||||
DeleteFileIfExists("component.dbf");
|
|
||||||
DeleteFileIfExists("component.shx");
|
|
||||||
DeleteFileIfExists("component.shp");
|
|
||||||
|
|
||||||
Percent p(m_node_based_graph->GetNumberOfNodes());
|
|
||||||
|
|
||||||
OGRRegisterAll();
|
|
||||||
|
|
||||||
const char *pszDriverName = "ESRI Shapefile";
|
|
||||||
OGRSFDriver *poDriver =
|
|
||||||
OGRSFDriverRegistrar::GetRegistrar()->GetDriverByName(pszDriverName);
|
|
||||||
if (nullptr == poDriver)
|
|
||||||
{
|
|
||||||
throw OSRMException("ESRI Shapefile driver not available");
|
|
||||||
}
|
|
||||||
OGRDataSource *poDS = poDriver->CreateDataSource("component.shp", nullptr);
|
|
||||||
|
|
||||||
if (nullptr == poDS)
|
|
||||||
{
|
|
||||||
throw OSRMException("Creation of output file failed");
|
|
||||||
}
|
|
||||||
|
|
||||||
OGRSpatialReference *poSRS = new OGRSpatialReference();
|
|
||||||
poSRS->importFromEPSG(4326);
|
|
||||||
|
|
||||||
OGRLayer *poLayer = poDS->CreateLayer("component", poSRS, wkbLineString, nullptr);
|
|
||||||
|
|
||||||
if (nullptr == poLayer)
|
|
||||||
{
|
|
||||||
throw OSRMException("Layer creation failed.");
|
|
||||||
}
|
|
||||||
TIMER_STOP(SCC_RUN_SETUP);
|
|
||||||
SimpleLogger().Write() << "shapefile setup took " << TIMER_MSEC(SCC_RUN_SETUP)/1000. << "s";
|
|
||||||
|
|
||||||
TIMER_START(SCC_RUN);
|
TIMER_START(SCC_RUN);
|
||||||
// The following is a hack to distinguish between stuff that happens
|
// The following is a hack to distinguish between stuff that happens
|
||||||
// before the recursive call and stuff that happens after
|
// before the recursive call and stuff that happens after
|
||||||
std::stack<TarjanStackFrame> recursion_stack;
|
std::stack<TarjanStackFrame> recursion_stack;
|
||||||
// true = stuff before, false = stuff after call
|
// true = stuff before, false = stuff after call
|
||||||
std::stack<NodeID> tarjan_stack;
|
std::stack<NodeID> tarjan_stack;
|
||||||
std::vector<unsigned> components_index(m_node_based_graph->GetNumberOfNodes(),
|
|
||||||
SPECIAL_NODEID);
|
|
||||||
std::vector<NodeID> component_size_vector;
|
|
||||||
std::vector<TarjanNode> tarjan_node_list(m_node_based_graph->GetNumberOfNodes());
|
std::vector<TarjanNode> tarjan_node_list(m_node_based_graph->GetNumberOfNodes());
|
||||||
unsigned component_index = 0, size_of_current_component = 0;
|
unsigned component_index = 0, size_of_current_component = 0;
|
||||||
int index = 0;
|
int index = 0;
|
||||||
@@ -274,8 +183,7 @@ class TarjanSCC
|
|||||||
// Traverse outgoing edges
|
// Traverse outgoing edges
|
||||||
for (const auto current_edge : m_node_based_graph->GetAdjacentEdgeRange(v))
|
for (const auto current_edge : m_node_based_graph->GetAdjacentEdgeRange(v))
|
||||||
{
|
{
|
||||||
const TarjanDynamicGraph::NodeIterator vprime =
|
const auto vprime = m_node_based_graph->GetTarget(current_edge);
|
||||||
m_node_based_graph->GetTarget(current_edge);
|
|
||||||
if (SPECIAL_NODEID == tarjan_node_list[vprime].index)
|
if (SPECIAL_NODEID == tarjan_node_list[vprime].index)
|
||||||
{
|
{
|
||||||
recursion_stack.emplace(TarjanStackFrame(vprime, v));
|
recursion_stack.emplace(TarjanStackFrame(vprime, v));
|
||||||
@@ -327,12 +235,10 @@ class TarjanSCC
|
|||||||
|
|
||||||
TIMER_STOP(SCC_RUN);
|
TIMER_STOP(SCC_RUN);
|
||||||
SimpleLogger().Write() << "SCC run took: " << TIMER_MSEC(SCC_RUN)/1000. << "s";
|
SimpleLogger().Write() << "SCC run took: " << TIMER_MSEC(SCC_RUN)/1000. << "s";
|
||||||
SimpleLogger().Write() << "identified: " << component_size_vector.size()
|
SimpleLogger().Write() << "identified: " << component_size_vector.size() << " many components";
|
||||||
<< " many components, marking small components";
|
|
||||||
|
|
||||||
TIMER_START(SCC_OUTPUT);
|
|
||||||
|
|
||||||
const unsigned size_one_counter = std::count_if(component_size_vector.begin(),
|
size_one_counter = std::count_if(component_size_vector.begin(),
|
||||||
component_size_vector.end(),
|
component_size_vector.end(),
|
||||||
[](unsigned value)
|
[](unsigned value)
|
||||||
{
|
{
|
||||||
@@ -341,72 +247,11 @@ class TarjanSCC
|
|||||||
|
|
||||||
SimpleLogger().Write() << "identified " << size_one_counter << " SCCs of size 1";
|
SimpleLogger().Write() << "identified " << size_one_counter << " SCCs of size 1";
|
||||||
|
|
||||||
uint64_t total_network_distance = 0;
|
|
||||||
p.reinit(m_node_based_graph->GetNumberOfNodes());
|
|
||||||
// const NodeID last_u_node = m_node_based_graph->GetNumberOfNodes();
|
|
||||||
for (const NodeID source : osrm::irange(0u, last_node))
|
|
||||||
{
|
|
||||||
p.printIncrement();
|
|
||||||
for (const auto current_edge : m_node_based_graph->GetAdjacentEdgeRange(source))
|
|
||||||
{
|
|
||||||
const TarjanDynamicGraph::NodeIterator target =
|
|
||||||
m_node_based_graph->GetTarget(current_edge);
|
|
||||||
|
|
||||||
if (source < target ||
|
|
||||||
m_node_based_graph->EndEdges(target) ==
|
|
||||||
m_node_based_graph->FindEdge(target, source))
|
|
||||||
{
|
|
||||||
total_network_distance +=
|
|
||||||
100 * FixedPointCoordinate::ApproximateEuclideanDistance(
|
|
||||||
m_coordinate_list[source].lat,
|
|
||||||
m_coordinate_list[source].lon,
|
|
||||||
m_coordinate_list[target].lat,
|
|
||||||
m_coordinate_list[target].lon);
|
|
||||||
|
|
||||||
BOOST_ASSERT(current_edge != SPECIAL_EDGEID);
|
|
||||||
BOOST_ASSERT(source != SPECIAL_NODEID);
|
|
||||||
BOOST_ASSERT(target != SPECIAL_NODEID);
|
|
||||||
|
|
||||||
const unsigned size_of_containing_component =
|
|
||||||
std::min(component_size_vector[components_index[source]],
|
|
||||||
component_size_vector[components_index[target]]);
|
|
||||||
|
|
||||||
// edges that end on bollard nodes may actually be in two distinct components
|
|
||||||
if (size_of_containing_component < 10)
|
|
||||||
{
|
|
||||||
OGRLineString lineString;
|
|
||||||
lineString.addPoint(m_coordinate_list[source].lon / COORDINATE_PRECISION,
|
|
||||||
m_coordinate_list[source].lat / COORDINATE_PRECISION);
|
|
||||||
lineString.addPoint(m_coordinate_list[target].lon / COORDINATE_PRECISION,
|
|
||||||
m_coordinate_list[target].lat / COORDINATE_PRECISION);
|
|
||||||
|
|
||||||
OGRFeature *poFeature = OGRFeature::CreateFeature(poLayer->GetLayerDefn());
|
|
||||||
|
|
||||||
poFeature->SetGeometry(&lineString);
|
|
||||||
if (OGRERR_NONE != poLayer->CreateFeature(poFeature))
|
|
||||||
{
|
|
||||||
throw OSRMException("Failed to create feature in shapefile.");
|
|
||||||
}
|
}
|
||||||
OGRFeature::DestroyFeature(poFeature);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}
|
|
||||||
OGRDataSource::DestroyDataSource(poDS);
|
|
||||||
component_size_vector.clear();
|
|
||||||
component_size_vector.shrink_to_fit();
|
|
||||||
BOOST_ASSERT_MSG(0 == component_size_vector.size() && 0 == component_size_vector.capacity(),
|
|
||||||
"component_size_vector not properly deallocated");
|
|
||||||
|
|
||||||
components_index.clear();
|
unsigned get_component_size(const NodeID node) const
|
||||||
components_index.shrink_to_fit();
|
{
|
||||||
BOOST_ASSERT_MSG(0 == components_index.size() && 0 == components_index.capacity(),
|
return component_size_vector[components_index[node]];
|
||||||
"components_index not properly deallocated");
|
|
||||||
TIMER_STOP(SCC_OUTPUT);
|
|
||||||
SimpleLogger().Write() << "generating output took: " << TIMER_MSEC(SCC_OUTPUT)/1000. << "s";
|
|
||||||
|
|
||||||
SimpleLogger().Write() << "total network distance: "
|
|
||||||
<< (uint64_t)total_network_distance / 100 / 1000. << " km";
|
|
||||||
}
|
}
|
||||||
|
|
||||||
private:
|
private:
|
||||||
@@ -446,14 +291,6 @@ class TarjanSCC
|
|||||||
}
|
}
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
void DeleteFileIfExists(const std::string &file_name) const
|
|
||||||
{
|
|
||||||
if (boost::filesystem::exists(file_name))
|
|
||||||
{
|
|
||||||
boost::filesystem::remove(file_name);
|
|
||||||
}
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* STRONGLYCONNECTEDCOMPONENTS_H_ */
|
#endif /* TINY_COMPONENTS_HPP */
|
||||||
+6
-1
@@ -38,13 +38,18 @@ build_script:
|
|||||||
- SET P=c:/projects/osrm
|
- SET P=c:/projects/osrm
|
||||||
- set TBB_INSTALL_DIR=%P%/tbb
|
- set TBB_INSTALL_DIR=%P%/tbb
|
||||||
- set TBB_ARCH_PLATFORM=intel64/vc12
|
- set TBB_ARCH_PLATFORM=intel64/vc12
|
||||||
- cmake .. -G "Visual Studio 12 Win64" -DCMAKE_BUILD_TYPE=%Configuration% -DBZIP2_INCLUDE_DIR=%P%/libs/include -DBZIP2_LIBRARIES=%P%/libs/lib/libbz2.lib -DCMAKE_INSTALL_PREFIX=%P%/libs -DBOOST_ROOT=%P%/boost_min -DBoost_USE_STATIC_LIBS=ON -T CTP_Nov2013
|
- cmake .. -G "Visual Studio 12 Win64" -DCMAKE_BUILD_TYPE=%Configuration% -DCMAKE_INSTALL_PREFIX=%P%/libs -DBOOST_ROOT=%P%/boost_min -DBoost_ADDITIONAL_VERSIONS=1.57 -DBoost_USE_STATIC_LIBS=ON -T CTP_Nov2013
|
||||||
- msbuild /clp:Verbosity=minimal /nologo OSRM.sln
|
- msbuild /clp:Verbosity=minimal /nologo OSRM.sln
|
||||||
- msbuild /clp:Verbosity=minimal /nologo tests.vcxproj
|
- msbuild /clp:Verbosity=minimal /nologo tests.vcxproj
|
||||||
|
- cd %Configuration%
|
||||||
- if "%APPVEYOR_REPO_BRANCH%"=="develop" (7z a %P%/osrm_%Configuration%.zip *.exe *.pdb %P%/libs/bin/*.dll -tzip)
|
- if "%APPVEYOR_REPO_BRANCH%"=="develop" (7z a %P%/osrm_%Configuration%.zip *.exe *.pdb %P%/libs/bin/*.dll -tzip)
|
||||||
|
- cd ..\..\profiles
|
||||||
|
- echo disk=c:\temp\stxxl,10000,wincall > .stxxl.txt
|
||||||
|
- if "%APPVEYOR_REPO_BRANCH%"=="develop" (7z a %P%/osrm_%Configuration%.zip * -tzip)
|
||||||
- set PATH=%PATH%;c:/projects/osrm/libs/bin
|
- set PATH=%PATH%;c:/projects/osrm/libs/bin
|
||||||
- cd c:/projects/osrm/build/%Configuration%
|
- cd c:/projects/osrm/build/%Configuration%
|
||||||
- datastructure-tests.exe
|
- datastructure-tests.exe
|
||||||
|
- algorithm-tests.exe
|
||||||
|
|
||||||
test: off
|
test: off
|
||||||
|
|
||||||
|
|||||||
@@ -0,0 +1,189 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "../data_structures/original_edge_data.hpp"
|
||||||
|
#include "../data_structures/query_node.hpp"
|
||||||
|
#include "../data_structures/shared_memory_vector_wrapper.hpp"
|
||||||
|
#include "../data_structures/static_rtree.hpp"
|
||||||
|
#include "../data_structures/edge_based_node.hpp"
|
||||||
|
#include "../Util/BoostFileSystemFix.h"
|
||||||
|
|
||||||
|
#include <osrm/Coordinate.h>
|
||||||
|
|
||||||
|
#include <random>
|
||||||
|
|
||||||
|
// Choosen by a fair W20 dice roll (this value is completely arbitrary)
|
||||||
|
constexpr unsigned RANDOM_SEED = 13;
|
||||||
|
constexpr int32_t WORLD_MIN_LAT = -90 * COORDINATE_PRECISION;
|
||||||
|
constexpr int32_t WORLD_MAX_LAT = 90 * COORDINATE_PRECISION;
|
||||||
|
constexpr int32_t WORLD_MIN_LON = -180 * COORDINATE_PRECISION;
|
||||||
|
constexpr int32_t WORLD_MAX_LON = 180 * COORDINATE_PRECISION;
|
||||||
|
|
||||||
|
using RTreeLeaf = EdgeBasedNode;
|
||||||
|
using FixedPointCoordinateListPtr = std::shared_ptr<std::vector<FixedPointCoordinate>>;
|
||||||
|
using BenchStaticRTree = StaticRTree<RTreeLeaf, ShM<FixedPointCoordinate, false>::vector, false>;
|
||||||
|
|
||||||
|
FixedPointCoordinateListPtr LoadCoordinates(const boost::filesystem::path &nodes_file)
|
||||||
|
{
|
||||||
|
boost::filesystem::ifstream nodes_input_stream(nodes_file, std::ios::binary);
|
||||||
|
|
||||||
|
QueryNode current_node;
|
||||||
|
unsigned number_of_coordinates = 0;
|
||||||
|
nodes_input_stream.read((char *)&number_of_coordinates, sizeof(unsigned));
|
||||||
|
auto coords = std::make_shared<std::vector<FixedPointCoordinate>>(number_of_coordinates);
|
||||||
|
for (unsigned i = 0; i < number_of_coordinates; ++i)
|
||||||
|
{
|
||||||
|
nodes_input_stream.read((char *)¤t_node, sizeof(QueryNode));
|
||||||
|
coords->at(i) = FixedPointCoordinate(current_node.lat, current_node.lon);
|
||||||
|
BOOST_ASSERT((std::abs(coords->at(i).lat) >> 30) == 0);
|
||||||
|
BOOST_ASSERT((std::abs(coords->at(i).lon) >> 30) == 0);
|
||||||
|
}
|
||||||
|
nodes_input_stream.close();
|
||||||
|
return coords;
|
||||||
|
}
|
||||||
|
|
||||||
|
void Benchmark(BenchStaticRTree &rtree, unsigned num_queries)
|
||||||
|
{
|
||||||
|
std::mt19937 mt_rand(RANDOM_SEED);
|
||||||
|
std::uniform_int_distribution<> lat_udist(WORLD_MIN_LAT, WORLD_MAX_LAT);
|
||||||
|
std::uniform_int_distribution<> lon_udist(WORLD_MIN_LON, WORLD_MAX_LON);
|
||||||
|
std::vector<FixedPointCoordinate> queries;
|
||||||
|
for (unsigned i = 0; i < num_queries; i++)
|
||||||
|
{
|
||||||
|
queries.emplace_back(FixedPointCoordinate(lat_udist(mt_rand), lon_udist(mt_rand)));
|
||||||
|
}
|
||||||
|
|
||||||
|
{
|
||||||
|
const unsigned num_results = 5;
|
||||||
|
std::cout << "#### IncrementalFindPhantomNodeForCoordinate : " << num_results
|
||||||
|
<< " phantom nodes"
|
||||||
|
<< "\n";
|
||||||
|
|
||||||
|
TIMER_START(query_phantom);
|
||||||
|
std::vector<PhantomNode> resulting_phantom_node_vector;
|
||||||
|
for (const auto &q : queries)
|
||||||
|
{
|
||||||
|
resulting_phantom_node_vector.clear();
|
||||||
|
rtree.IncrementalFindPhantomNodeForCoordinate(
|
||||||
|
q, resulting_phantom_node_vector, 3, num_results);
|
||||||
|
resulting_phantom_node_vector.clear();
|
||||||
|
rtree.IncrementalFindPhantomNodeForCoordinate(
|
||||||
|
q, resulting_phantom_node_vector, 17, num_results);
|
||||||
|
}
|
||||||
|
TIMER_STOP(query_phantom);
|
||||||
|
|
||||||
|
std::cout << "Took " << TIMER_MSEC(query_phantom) << " msec for " << num_queries
|
||||||
|
<< " queries."
|
||||||
|
<< "\n";
|
||||||
|
std::cout << TIMER_MSEC(query_phantom) / ((double)num_queries) << " msec/query."
|
||||||
|
<< "\n";
|
||||||
|
|
||||||
|
std::cout << "#### LocateClosestEndPointForCoordinate"
|
||||||
|
<< "\n";
|
||||||
|
}
|
||||||
|
|
||||||
|
TIMER_START(query_endpoint);
|
||||||
|
FixedPointCoordinate result;
|
||||||
|
for (const auto &q : queries)
|
||||||
|
{
|
||||||
|
rtree.LocateClosestEndPointForCoordinate(q, result, 3);
|
||||||
|
}
|
||||||
|
TIMER_STOP(query_endpoint);
|
||||||
|
|
||||||
|
std::cout << "Took " << TIMER_MSEC(query_endpoint) << " msec for " << num_queries << " queries."
|
||||||
|
<< "\n";
|
||||||
|
std::cout << TIMER_MSEC(query_endpoint) / ((double)num_queries) << " msec/query."
|
||||||
|
<< "\n";
|
||||||
|
|
||||||
|
std::cout << "#### FindPhantomNodeForCoordinate"
|
||||||
|
<< "\n";
|
||||||
|
|
||||||
|
TIMER_START(query_phantomnode);
|
||||||
|
for (const auto &q : queries)
|
||||||
|
{
|
||||||
|
PhantomNode phantom;
|
||||||
|
rtree.FindPhantomNodeForCoordinate(q, phantom, 3);
|
||||||
|
}
|
||||||
|
TIMER_STOP(query_phantomnode);
|
||||||
|
|
||||||
|
std::cout << "Took " << TIMER_MSEC(query_phantomnode) << " msec for " << num_queries
|
||||||
|
<< " queries."
|
||||||
|
<< "\n";
|
||||||
|
std::cout << TIMER_MSEC(query_phantomnode) / ((double)num_queries) << " msec/query."
|
||||||
|
<< "\n";
|
||||||
|
|
||||||
|
{
|
||||||
|
const unsigned num_results = 1;
|
||||||
|
std::cout << "#### IncrementalFindPhantomNodeForCoordinate : " << num_results
|
||||||
|
<< " phantom nodes"
|
||||||
|
<< "\n";
|
||||||
|
|
||||||
|
TIMER_START(query_phantom);
|
||||||
|
std::vector<PhantomNode> resulting_phantom_node_vector;
|
||||||
|
for (const auto &q : queries)
|
||||||
|
{
|
||||||
|
resulting_phantom_node_vector.clear();
|
||||||
|
rtree.IncrementalFindPhantomNodeForCoordinate(
|
||||||
|
q, resulting_phantom_node_vector, 3, num_results);
|
||||||
|
resulting_phantom_node_vector.clear();
|
||||||
|
rtree.IncrementalFindPhantomNodeForCoordinate(
|
||||||
|
q, resulting_phantom_node_vector, 17, num_results);
|
||||||
|
}
|
||||||
|
TIMER_STOP(query_phantom);
|
||||||
|
|
||||||
|
std::cout << "Took " << TIMER_MSEC(query_phantom) << " msec for " << num_queries
|
||||||
|
<< " queries."
|
||||||
|
<< "\n";
|
||||||
|
std::cout << TIMER_MSEC(query_phantom) / ((double)num_queries) << " msec/query."
|
||||||
|
<< "\n";
|
||||||
|
|
||||||
|
std::cout << "#### LocateClosestEndPointForCoordinate"
|
||||||
|
<< "\n";
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
int main(int argc, char **argv)
|
||||||
|
{
|
||||||
|
if (argc < 4)
|
||||||
|
{
|
||||||
|
std::cout << "./rtree-bench file.ramIndex file.fileIndx file.nodes"
|
||||||
|
<< "\n";
|
||||||
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
|
const char *ramPath = argv[1];
|
||||||
|
const char *filePath = argv[2];
|
||||||
|
const char *nodesPath = argv[3];
|
||||||
|
|
||||||
|
auto coords = LoadCoordinates(nodesPath);
|
||||||
|
|
||||||
|
BenchStaticRTree rtree(ramPath, filePath, coords);
|
||||||
|
|
||||||
|
Benchmark(rtree, 10000);
|
||||||
|
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
@@ -3,8 +3,8 @@ if (EXISTS ${OLDFILE})
|
|||||||
file(REMOVE_RECURSE ${OLDFILE})
|
file(REMOVE_RECURSE ${OLDFILE})
|
||||||
endif()
|
endif()
|
||||||
file(MD5 ${SOURCE_DIR}/prepare.cpp MD5PREPARE)
|
file(MD5 ${SOURCE_DIR}/prepare.cpp MD5PREPARE)
|
||||||
file(MD5 ${SOURCE_DIR}/DataStructures/StaticRTree.h MD5RTREE)
|
file(MD5 ${SOURCE_DIR}/data_structures/static_rtree.hpp MD5RTREE)
|
||||||
file(MD5 ${SOURCE_DIR}/Util/GraphLoader.h MD5GRAPH)
|
file(MD5 ${SOURCE_DIR}/Util/graph_loader.hpp MD5GRAPH)
|
||||||
file(MD5 ${SOURCE_DIR}/Server/DataStructures/InternalDataFacade.h MD5OBJECTS)
|
file(MD5 ${SOURCE_DIR}/Server/DataStructures/InternalDataFacade.h MD5OBJECTS)
|
||||||
|
|
||||||
CONFIGURE_FILE( ${SOURCE_DIR}/Util/FingerPrint.cpp.in ${SOURCE_DIR}/Util/FingerPrint.cpp )
|
CONFIGURE_FILE( ${SOURCE_DIR}/Util/finger_print.cpp.in ${SOURCE_DIR}/Util/finger_print.cpp )
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,20 +25,20 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef CONTRACTOR_H
|
#ifndef CONTRACTOR_HPP
|
||||||
#define CONTRACTOR_H
|
#define CONTRACTOR_HPP
|
||||||
|
|
||||||
#include "../DataStructures/BinaryHeap.h"
|
#include "../data_structures/binary_heap.hpp"
|
||||||
#include "../DataStructures/DeallocatingVector.h"
|
#include "../data_structures/deallocating_vector.hpp"
|
||||||
#include "../DataStructures/DynamicGraph.h"
|
#include "../data_structures/dynamic_graph.hpp"
|
||||||
#include "../DataStructures/Percent.h"
|
#include "../data_structures/percent.hpp"
|
||||||
#include "../DataStructures/QueryEdge.h"
|
#include "../data_structures/query_edge.hpp"
|
||||||
#include "../DataStructures/Range.h"
|
#include "../data_structures/xor_fast_hash.hpp"
|
||||||
#include "../DataStructures/XORFastHash.h"
|
#include "../data_structures/xor_fast_hash_storage.hpp"
|
||||||
#include "../DataStructures/XORFastHashStorage.h"
|
#include "../Util/integer_range.hpp"
|
||||||
#include "../Util/simple_logger.hpp"
|
#include "../Util/simple_logger.hpp"
|
||||||
#include "../Util/StringUtil.h"
|
#include "../Util/StringUtil.h"
|
||||||
#include "../Util/TimingUtil.h"
|
#include "../Util/timing_util.hpp"
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|
||||||
#include <boost/assert.hpp>
|
#include <boost/assert.hpp>
|
||||||
@@ -970,4 +970,4 @@ class Contractor
|
|||||||
XORFastHash fast_hash;
|
XORFastHash fast_hash;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // CONTRACTOR_H
|
#endif // CONTRACTOR_HPP
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,14 +25,14 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "EdgeBasedGraphFactory.h"
|
#include "edge_based_graph_factory.hpp"
|
||||||
#include "../Algorithms/BFSComponentExplorer.h"
|
#include "../algorithms/bfs_components.hpp"
|
||||||
#include "../DataStructures/Percent.h"
|
#include "../data_structures/percent.hpp"
|
||||||
#include "../DataStructures/Range.h"
|
|
||||||
#include "../Util/compute_angle.hpp"
|
#include "../Util/compute_angle.hpp"
|
||||||
#include "../Util/LuaUtil.h"
|
#include "../Util/integer_range.hpp"
|
||||||
|
#include "../Util/lua_util.hpp"
|
||||||
#include "../Util/simple_logger.hpp"
|
#include "../Util/simple_logger.hpp"
|
||||||
#include "../Util/TimingUtil.h"
|
#include "../Util/timing_util.hpp"
|
||||||
|
|
||||||
#include <boost/assert.hpp>
|
#include <boost/assert.hpp>
|
||||||
|
|
||||||
@@ -45,7 +45,7 @@ EdgeBasedGraphFactory::EdgeBasedGraphFactory(
|
|||||||
std::unique_ptr<RestrictionMap> restriction_map,
|
std::unique_ptr<RestrictionMap> restriction_map,
|
||||||
std::vector<NodeID> &barrier_node_list,
|
std::vector<NodeID> &barrier_node_list,
|
||||||
std::vector<NodeID> &traffic_light_node_list,
|
std::vector<NodeID> &traffic_light_node_list,
|
||||||
std::vector<NodeInfo> &node_info_list,
|
std::vector<QueryNode> &node_info_list,
|
||||||
SpeedProfileProperties &speed_profile)
|
SpeedProfileProperties &speed_profile)
|
||||||
: speed_profile(speed_profile),
|
: speed_profile(speed_profile),
|
||||||
m_number_of_edge_based_nodes(std::numeric_limits<unsigned>::max()),
|
m_number_of_edge_based_nodes(std::numeric_limits<unsigned>::max()),
|
||||||
@@ -123,7 +123,7 @@ EdgeBasedGraphFactory::InsertEdgeBasedNode(const NodeID node_u, const NodeID nod
|
|||||||
m_geometry_compressor.GetBucketReference(e2);
|
m_geometry_compressor.GetBucketReference(e2);
|
||||||
BOOST_ASSERT(forward_geometry.size() == reverse_geometry.size());
|
BOOST_ASSERT(forward_geometry.size() == reverse_geometry.size());
|
||||||
BOOST_ASSERT(0 != forward_geometry.size());
|
BOOST_ASSERT(0 != forward_geometry.size());
|
||||||
const unsigned geometry_size = forward_geometry.size();
|
const unsigned geometry_size = static_cast<unsigned>(forward_geometry.size());
|
||||||
BOOST_ASSERT(geometry_size > 1);
|
BOOST_ASSERT(geometry_size > 1);
|
||||||
|
|
||||||
// reconstruct bidirectional edge with individual weights and put each into the NN index
|
// reconstruct bidirectional edge with individual weights and put each into the NN index
|
||||||
@@ -389,10 +389,10 @@ void EdgeBasedGraphFactory::CompressGeometry()
|
|||||||
|
|
||||||
// update any involved turn restrictions
|
// update any involved turn restrictions
|
||||||
m_restriction_map->FixupStartingTurnRestriction(node_u, node_v, node_w);
|
m_restriction_map->FixupStartingTurnRestriction(node_u, node_v, node_w);
|
||||||
m_restriction_map->FixupArrivingTurnRestriction(node_u, node_v, node_w);
|
m_restriction_map->FixupArrivingTurnRestriction(node_u, node_v, node_w, m_node_based_graph);
|
||||||
|
|
||||||
m_restriction_map->FixupStartingTurnRestriction(node_w, node_v, node_u);
|
m_restriction_map->FixupStartingTurnRestriction(node_w, node_v, node_u);
|
||||||
m_restriction_map->FixupArrivingTurnRestriction(node_w, node_v, node_u);
|
m_restriction_map->FixupArrivingTurnRestriction(node_w, node_v, node_u, m_node_based_graph);
|
||||||
|
|
||||||
// store compressed geometry in container
|
// store compressed geometry in container
|
||||||
m_geometry_compressor.CompressEdge(
|
m_geometry_compressor.CompressEdge(
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -27,18 +27,18 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
// This class constructs the edge-expanded routing graph
|
// This class constructs the edge-expanded routing graph
|
||||||
|
|
||||||
#ifndef EDGEBASEDGRAPHFACTORY_H_
|
#ifndef EDGE_BASED_GRAPH_FACTORY_HPP_
|
||||||
#define EDGEBASEDGRAPHFACTORY_H_
|
#define EDGE_BASED_GRAPH_FACTORY_HPP_
|
||||||
|
|
||||||
|
#include "geometry_compressor.hpp"
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
#include "../DataStructures/DeallocatingVector.h"
|
#include "../data_structures/deallocating_vector.hpp"
|
||||||
#include "../DataStructures/EdgeBasedNode.h"
|
#include "../data_structures/edge_based_node.hpp"
|
||||||
#include "../DataStructures/OriginalEdgeData.h"
|
#include "../data_structures/original_edge_data.hpp"
|
||||||
#include "../DataStructures/QueryNode.h"
|
#include "../data_structures/query_node.hpp"
|
||||||
#include "../DataStructures/TurnInstructions.h"
|
#include "../data_structures/turn_instructions.hpp"
|
||||||
#include "../DataStructures/NodeBasedGraph.h"
|
#include "../data_structures/node_based_graph.hpp"
|
||||||
#include "../DataStructures/RestrictionMap.h"
|
#include "../data_structures/restriction_map.hpp"
|
||||||
#include "GeometryCompressor.h"
|
|
||||||
|
|
||||||
#include <algorithm>
|
#include <algorithm>
|
||||||
#include <iosfwd>
|
#include <iosfwd>
|
||||||
@@ -63,7 +63,7 @@ class EdgeBasedGraphFactory
|
|||||||
std::unique_ptr<RestrictionMap> restricion_map,
|
std::unique_ptr<RestrictionMap> restricion_map,
|
||||||
std::vector<NodeID> &barrier_node_list,
|
std::vector<NodeID> &barrier_node_list,
|
||||||
std::vector<NodeID> &traffic_light_node_list,
|
std::vector<NodeID> &traffic_light_node_list,
|
||||||
std::vector<NodeInfo> &m_node_info_list,
|
std::vector<QueryNode> &node_info_list,
|
||||||
SpeedProfileProperties &speed_profile);
|
SpeedProfileProperties &speed_profile);
|
||||||
|
|
||||||
void Run(const std::string &original_edge_data_filename,
|
void Run(const std::string &original_edge_data_filename,
|
||||||
@@ -97,7 +97,7 @@ class EdgeBasedGraphFactory
|
|||||||
|
|
||||||
unsigned m_number_of_edge_based_nodes;
|
unsigned m_number_of_edge_based_nodes;
|
||||||
|
|
||||||
std::vector<NodeInfo> m_node_info_list;
|
std::vector<QueryNode> m_node_info_list;
|
||||||
std::vector<EdgeBasedNode> m_edge_based_node_list;
|
std::vector<EdgeBasedNode> m_edge_based_node_list;
|
||||||
DeallocatingVector<EdgeBasedEdge> m_edge_based_edge_list;
|
DeallocatingVector<EdgeBasedEdge> m_edge_based_edge_list;
|
||||||
|
|
||||||
@@ -123,4 +123,4 @@ class EdgeBasedGraphFactory
|
|||||||
NodeID max_id;
|
NodeID max_id;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* EDGEBASEDGRAPHFACTORY_H_ */
|
#endif /* EDGE_BASED_GRAPH_FACTORY_HPP_ */
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,7 +25,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "GeometryCompressor.h"
|
#include "geometry_compressor.hpp"
|
||||||
#include "../Util/simple_logger.hpp"
|
#include "../Util/simple_logger.hpp"
|
||||||
|
|
||||||
#include <boost/assert.hpp>
|
#include <boost/assert.hpp>
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef GEOMETRY_COMPRESSOR_H
|
#ifndef GEOMETRY_COMPRESSOR_HPP_
|
||||||
#define GEOMETRY_COMPRESSOR_H
|
#define GEOMETRY_COMPRESSOR_HPP_
|
||||||
|
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|
||||||
@@ -64,4 +64,4 @@ class GeometryCompressor
|
|||||||
std::unordered_map<EdgeID, unsigned> m_edge_id_to_list_index_map;
|
std::unordered_map<EdgeID, unsigned> m_edge_id_to_list_index_map;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // GEOMETRY_COMPRESSOR_H
|
#endif // GEOMETRY_COMPRESSOR_HPP_
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,24 +25,24 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "Prepare.h"
|
#include "processing_chain.hpp"
|
||||||
|
|
||||||
#include "Contractor.h"
|
#include "contractor.hpp"
|
||||||
|
|
||||||
#include "../Algorithms/IteratorBasedCRC32.h"
|
#include "../algorithms/crc32_processor.hpp"
|
||||||
#include "../DataStructures/BinaryHeap.h"
|
#include "../data_structures/deallocating_vector.hpp"
|
||||||
#include "../DataStructures/DeallocatingVector.h"
|
#include "../data_structures/static_rtree.hpp"
|
||||||
#include "../DataStructures/Range.h"
|
#include "../data_structures/restriction_map.hpp"
|
||||||
#include "../DataStructures/StaticRTree.h"
|
|
||||||
#include "../DataStructures/RestrictionMap.h"
|
|
||||||
|
|
||||||
#include "../Util/GitDescription.h"
|
#include "../Util/GitDescription.h"
|
||||||
#include "../Util/LuaUtil.h"
|
#include "../Util/graph_loader.hpp"
|
||||||
|
#include "../Util/integer_range.hpp"
|
||||||
|
#include "../Util/lua_util.hpp"
|
||||||
#include "../Util/make_unique.hpp"
|
#include "../Util/make_unique.hpp"
|
||||||
#include "../Util/OSRMException.h"
|
#include "../Util/OSRMException.h"
|
||||||
#include "../Util/simple_logger.hpp"
|
#include "../Util/simple_logger.hpp"
|
||||||
#include "../Util/StringUtil.h"
|
#include "../Util/StringUtil.h"
|
||||||
#include "../Util/TimingUtil.h"
|
#include "../Util/timing_util.hpp"
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|
||||||
#include <boost/filesystem/fstream.hpp>
|
#include <boost/filesystem/fstream.hpp>
|
||||||
@@ -394,6 +394,13 @@ bool Prepare::ParseArguments(int argc, char *argv[])
|
|||||||
.run(),
|
.run(),
|
||||||
option_variables);
|
option_variables);
|
||||||
|
|
||||||
|
const auto& temp_config_path = option_variables["config"].as<boost::filesystem::path>();
|
||||||
|
if (boost::filesystem::is_regular_file(temp_config_path))
|
||||||
|
{
|
||||||
|
boost::program_options::store(boost::program_options::parse_config_file<char>(temp_config_path.string().c_str(), cmdline_options, true),
|
||||||
|
option_variables);
|
||||||
|
}
|
||||||
|
|
||||||
if (option_variables.count("version"))
|
if (option_variables.count("version"))
|
||||||
{
|
{
|
||||||
SimpleLogger().Write() << g_GIT_DESCRIPTION;
|
SimpleLogger().Write() << g_GIT_DESCRIPTION;
|
||||||
@@ -502,8 +509,7 @@ Prepare::BuildEdgeExpandedGraph(lua_State *lua_state,
|
|||||||
SimpleLogger().Write() << "Generating edge-expanded graph representation";
|
SimpleLogger().Write() << "Generating edge-expanded graph representation";
|
||||||
std::shared_ptr<NodeBasedDynamicGraph> node_based_graph =
|
std::shared_ptr<NodeBasedDynamicGraph> node_based_graph =
|
||||||
NodeBasedDynamicGraphFromImportEdges(number_of_node_based_nodes, edge_list);
|
NodeBasedDynamicGraphFromImportEdges(number_of_node_based_nodes, edge_list);
|
||||||
std::unique_ptr<RestrictionMap> restriction_map =
|
std::unique_ptr<RestrictionMap> restriction_map = osrm::make_unique<RestrictionMap>(restriction_list);
|
||||||
std::unique_ptr<RestrictionMap>(new RestrictionMap(node_based_graph, restriction_list));
|
|
||||||
std::shared_ptr<EdgeBasedGraphFactory> edge_based_graph_factory =
|
std::shared_ptr<EdgeBasedGraphFactory> edge_based_graph_factory =
|
||||||
std::make_shared<EdgeBasedGraphFactory>(node_based_graph,
|
std::make_shared<EdgeBasedGraphFactory>(node_based_graph,
|
||||||
std::move(restriction_map),
|
std::move(restriction_map),
|
||||||
@@ -553,7 +559,7 @@ void Prepare::WriteNodeMapping()
|
|||||||
if (size_of_mapping > 0)
|
if (size_of_mapping > 0)
|
||||||
{
|
{
|
||||||
node_stream.write((char *)&(internal_to_external_node_map[0]),
|
node_stream.write((char *)&(internal_to_external_node_map[0]),
|
||||||
size_of_mapping * sizeof(NodeInfo));
|
size_of_mapping * sizeof(QueryNode));
|
||||||
}
|
}
|
||||||
node_stream.close();
|
node_stream.close();
|
||||||
internal_to_external_node_map.clear();
|
internal_to_external_node_map.clear();
|
||||||
@@ -1,15 +1,43 @@
|
|||||||
#ifndef PREPARE_H
|
/*
|
||||||
#define PREPARE_H
|
|
||||||
|
|
||||||
#include "EdgeBasedGraphFactory.h"
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
#include "../DataStructures/QueryEdge.h"
|
All rights reserved.
|
||||||
#include "../DataStructures/StaticGraph.h"
|
|
||||||
#include "../Util/GraphLoader.h"
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef PROCESSING_CHAIN_HPP
|
||||||
|
#define PROCESSING_CHAIN_HPP
|
||||||
|
|
||||||
|
#include "edge_based_graph_factory.hpp"
|
||||||
|
#include "../data_structures/query_edge.hpp"
|
||||||
|
#include "../data_structures/static_graph.hpp"
|
||||||
|
|
||||||
|
class FingerPrint;
|
||||||
|
struct EdgeBasedNode;
|
||||||
|
struct lua_State;
|
||||||
|
|
||||||
#include <boost/filesystem.hpp>
|
#include <boost/filesystem.hpp>
|
||||||
|
|
||||||
#include <luabind/luabind.hpp>
|
|
||||||
|
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -42,7 +70,7 @@ class Prepare
|
|||||||
void BuildRTree(std::vector<EdgeBasedNode> &node_based_edge_list);
|
void BuildRTree(std::vector<EdgeBasedNode> &node_based_edge_list);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
std::vector<NodeInfo> internal_to_external_node_map;
|
std::vector<QueryNode> internal_to_external_node_map;
|
||||||
std::vector<TurnRestriction> restriction_list;
|
std::vector<TurnRestriction> restriction_list;
|
||||||
std::vector<NodeID> barrier_node_list;
|
std::vector<NodeID> barrier_node_list;
|
||||||
std::vector<NodeID> traffic_light_list;
|
std::vector<NodeID> traffic_light_list;
|
||||||
@@ -64,4 +92,4 @@ class Prepare
|
|||||||
std::string rtree_leafs_path;
|
std::string rtree_leafs_path;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // PREPARE_H
|
#endif // PROCESSING_CHAIN_HPP
|
||||||
@@ -72,7 +72,7 @@ bool FixedPointCoordinate::isSet() const
|
|||||||
{
|
{
|
||||||
return (std::numeric_limits<int>::min() != lat) && (std::numeric_limits<int>::min() != lon);
|
return (std::numeric_limits<int>::min() != lat) && (std::numeric_limits<int>::min() != lon);
|
||||||
}
|
}
|
||||||
bool FixedPointCoordinate::isValid() const
|
bool FixedPointCoordinate::is_valid() const
|
||||||
{
|
{
|
||||||
if (lat > 90 * COORDINATE_PRECISION || lat < -90 * COORDINATE_PRECISION ||
|
if (lat > 90 * COORDINATE_PRECISION || lat < -90 * COORDINATE_PRECISION ||
|
||||||
lon > 180 * COORDINATE_PRECISION || lon < -180 * COORDINATE_PRECISION)
|
lon > 180 * COORDINATE_PRECISION || lon < -180 * COORDINATE_PRECISION)
|
||||||
@@ -246,7 +246,7 @@ FixedPointCoordinate::ComputePerpendicularDistance(const FixedPointCoordinate &s
|
|||||||
nearest_location.lon = static_cast<int>(q * COORDINATE_PRECISION);
|
nearest_location.lon = static_cast<int>(q * COORDINATE_PRECISION);
|
||||||
}
|
}
|
||||||
|
|
||||||
BOOST_ASSERT(nearest_location.isValid());
|
BOOST_ASSERT(nearest_location.is_valid());
|
||||||
return FixedPointCoordinate::ApproximateEuclideanDistance(point, nearest_location);
|
return FixedPointCoordinate::ApproximateEuclideanDistance(point, nearest_location);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -256,7 +256,7 @@ float FixedPointCoordinate::ComputePerpendicularDistance(const FixedPointCoordin
|
|||||||
FixedPointCoordinate &nearest_location,
|
FixedPointCoordinate &nearest_location,
|
||||||
float &ratio)
|
float &ratio)
|
||||||
{
|
{
|
||||||
BOOST_ASSERT(query_location.isValid());
|
BOOST_ASSERT(query_location.is_valid());
|
||||||
|
|
||||||
// initialize values
|
// initialize values
|
||||||
const double x = lat2y(query_location.lat / COORDINATE_PRECISION);
|
const double x = lat2y(query_location.lat / COORDINATE_PRECISION);
|
||||||
@@ -319,7 +319,7 @@ float FixedPointCoordinate::ComputePerpendicularDistance(const FixedPointCoordin
|
|||||||
nearest_location.lat = static_cast<int>(y2lat(p) * COORDINATE_PRECISION);
|
nearest_location.lat = static_cast<int>(y2lat(p) * COORDINATE_PRECISION);
|
||||||
nearest_location.lon = static_cast<int>(q * COORDINATE_PRECISION);
|
nearest_location.lon = static_cast<int>(q * COORDINATE_PRECISION);
|
||||||
}
|
}
|
||||||
BOOST_ASSERT(nearest_location.isValid());
|
BOOST_ASSERT(nearest_location.is_valid());
|
||||||
|
|
||||||
const float approximate_distance =
|
const float approximate_distance =
|
||||||
FixedPointCoordinate::ApproximateEuclideanDistance(query_location, nearest_location);
|
FixedPointCoordinate::ApproximateEuclideanDistance(query_location, nearest_location);
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef CONCURRENT_QUEUE_H
|
#ifndef CONCURRENT_QUEUE_HPP
|
||||||
#define CONCURRENT_QUEUE_H
|
#define CONCURRENT_QUEUE_HPP
|
||||||
|
|
||||||
#include <boost/circular_buffer.hpp>
|
#include <boost/circular_buffer.hpp>
|
||||||
#include <condition_variable>
|
#include <condition_variable>
|
||||||
@@ -80,4 +80,4 @@ template <typename Data> class ConcurrentQueue
|
|||||||
std::condition_variable m_not_full;
|
std::condition_variable m_not_full;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // CONCURRENT_QUEUE_H
|
#endif // CONCURRENT_QUEUE_HPP
|
||||||
@@ -28,7 +28,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
#ifndef DEALLOCATINGVECTOR_H_
|
#ifndef DEALLOCATINGVECTOR_H_
|
||||||
#define DEALLOCATINGVECTOR_H_
|
#define DEALLOCATINGVECTOR_H_
|
||||||
|
|
||||||
#include "Range.h"
|
#include "../Util/integer_range.hpp"
|
||||||
|
|
||||||
#include <boost/iterator/iterator_facade.hpp>
|
#include <boost/iterator/iterator_facade.hpp>
|
||||||
|
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,11 +25,11 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef DYNAMICGRAPH_H
|
#ifndef DYNAMICGRAPH_HPP
|
||||||
#define DYNAMICGRAPH_H
|
#define DYNAMICGRAPH_HPP
|
||||||
|
|
||||||
#include "DeallocatingVector.h"
|
#include "deallocating_vector.hpp"
|
||||||
#include "Range.h"
|
#include "../Util/integer_range.hpp"
|
||||||
|
|
||||||
#include <boost/assert.hpp>
|
#include <boost/assert.hpp>
|
||||||
|
|
||||||
@@ -100,7 +100,7 @@ template <typename EdgeDataT> class DynamicGraph
|
|||||||
position += node_list[node].edges;
|
position += node_list[node].edges;
|
||||||
}
|
}
|
||||||
node_list.back().firstEdge = position;
|
node_list.back().firstEdge = position;
|
||||||
edge_list.reserve((std::size_t)edge_list.size() * 1.1);
|
edge_list.reserve(static_cast<std::size_t>(edge_list.size() * 1.1));
|
||||||
edge_list.resize(position);
|
edge_list.resize(position);
|
||||||
edge = 0;
|
edge = 0;
|
||||||
for (const auto node : osrm::irange(0u, number_of_nodes))
|
for (const auto node : osrm::irange(0u, number_of_nodes))
|
||||||
@@ -292,4 +292,4 @@ template <typename EdgeDataT> class DynamicGraph
|
|||||||
DeallocatingVector<Edge> edge_list;
|
DeallocatingVector<Edge> edge_list;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // DYNAMICGRAPH_H
|
#endif // DYNAMICGRAPH_HPP
|
||||||
@@ -1,7 +1,34 @@
|
|||||||
#ifndef EDGE_BASED_NODE_H
|
/*
|
||||||
#define EDGE_BASED_NODE_H
|
|
||||||
|
|
||||||
#include "../DataStructures/TravelMode.h"
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef EDGE_BASED_NODE_HPP
|
||||||
|
#define EDGE_BASED_NODE_HPP
|
||||||
|
|
||||||
|
#include "../data_structures/travel_mode.hpp"
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
#include <osrm/Coordinate.h>
|
||||||
@@ -95,4 +122,4 @@ struct EdgeBasedNode
|
|||||||
TravelMode backward_travel_mode : 4;
|
TravelMode backward_travel_mode : 4;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif //EDGE_BASED_NODE_H
|
#endif //EDGE_BASED_NODE_HPP
|
||||||
@@ -25,19 +25,17 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "ImportNode.h"
|
#include "external_memory_node.hpp"
|
||||||
|
|
||||||
#include <limits>
|
#include <limits>
|
||||||
|
|
||||||
ExternalMemoryNode::ExternalMemoryNode(
|
ExternalMemoryNode::ExternalMemoryNode(
|
||||||
int lat, int lon, unsigned int node_id, bool bollard, bool traffic_light)
|
int lat, int lon, unsigned int node_id, bool barrier, bool traffic_lights)
|
||||||
: NodeInfo(lat, lon, node_id), bollard(bollard), trafficLight(traffic_light)
|
: QueryNode(lat, lon, node_id), barrier(barrier), traffic_lights(traffic_lights)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
ExternalMemoryNode::ExternalMemoryNode() : bollard(false), trafficLight(false)
|
ExternalMemoryNode::ExternalMemoryNode() : barrier(false), traffic_lights(false) {}
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
ExternalMemoryNode ExternalMemoryNode::min_value()
|
ExternalMemoryNode ExternalMemoryNode::min_value()
|
||||||
{
|
{
|
||||||
@@ -53,12 +51,18 @@ ExternalMemoryNode ExternalMemoryNode::max_value()
|
|||||||
false);
|
false);
|
||||||
}
|
}
|
||||||
|
|
||||||
void ImportNode::Clear()
|
bool ExternalMemoryNodeSTXXLCompare::operator()(const ExternalMemoryNode &left,
|
||||||
|
const ExternalMemoryNode &right) const
|
||||||
{
|
{
|
||||||
keyVals.Clear();
|
return left.node_id < right.node_id;
|
||||||
lat = 0;
|
}
|
||||||
lon = 0;
|
|
||||||
node_id = 0;
|
ExternalMemoryNodeSTXXLCompare::value_type ExternalMemoryNodeSTXXLCompare::max_value()
|
||||||
bollard = false;
|
{
|
||||||
trafficLight = false;
|
return ExternalMemoryNode::max_value();
|
||||||
|
}
|
||||||
|
|
||||||
|
ExternalMemoryNodeSTXXLCompare::value_type ExternalMemoryNodeSTXXLCompare::min_value()
|
||||||
|
{
|
||||||
|
return ExternalMemoryNode::min_value();
|
||||||
}
|
}
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,17 +25,16 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef IMPORTNODE_H_
|
#ifndef EXTERNAL_MEMORY_NODE_HPP_
|
||||||
#define IMPORTNODE_H_
|
#define EXTERNAL_MEMORY_NODE_HPP_
|
||||||
|
|
||||||
#include "QueryNode.h"
|
#include "query_node.hpp"
|
||||||
#include "../DataStructures/HashTable.h"
|
|
||||||
|
|
||||||
#include <string>
|
#include <string>
|
||||||
|
|
||||||
struct ExternalMemoryNode : NodeInfo
|
struct ExternalMemoryNode : QueryNode
|
||||||
{
|
{
|
||||||
ExternalMemoryNode(int lat, int lon, unsigned int id, bool bollard, bool traffic_light);
|
ExternalMemoryNode(int lat, int lon, NodeID id, bool barrier, bool traffic_light);
|
||||||
|
|
||||||
ExternalMemoryNode();
|
ExternalMemoryNode();
|
||||||
|
|
||||||
@@ -43,15 +42,16 @@ struct ExternalMemoryNode : NodeInfo
|
|||||||
|
|
||||||
static ExternalMemoryNode max_value();
|
static ExternalMemoryNode max_value();
|
||||||
|
|
||||||
bool bollard;
|
bool barrier;
|
||||||
bool trafficLight;
|
bool traffic_lights;
|
||||||
};
|
};
|
||||||
|
|
||||||
struct ImportNode : public ExternalMemoryNode
|
struct ExternalMemoryNodeSTXXLCompare
|
||||||
{
|
{
|
||||||
HashTable<std::string, std::string> keyVals;
|
using value_type = ExternalMemoryNode;
|
||||||
|
bool operator()(const ExternalMemoryNode &left, const ExternalMemoryNode &right) const;
|
||||||
inline void Clear();
|
value_type max_value();
|
||||||
|
value_type min_value();
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* IMPORTNODE_H_ */
|
#endif /* EXTERNAL_MEMORY_NODE_HPP_ */
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef OSRM_FIXED_POINT_NUMBER_H
|
#ifndef FIXED_POINT_NUMBER_HPP
|
||||||
#define OSRM_FIXED_POINT_NUMBER_H
|
#define FIXED_POINT_NUMBER_HPP
|
||||||
|
|
||||||
#include <cmath>
|
#include <cmath>
|
||||||
#include <cstdint>
|
#include <cstdint>
|
||||||
@@ -213,4 +213,4 @@ class FixedPointNumber
|
|||||||
|
|
||||||
static_assert(4 == sizeof(FixedPointNumber<1>), "FP19 has wrong size != 4");
|
static_assert(4 == sizeof(FixedPointNumber<1>), "FP19 has wrong size != 4");
|
||||||
}
|
}
|
||||||
#endif // OSRM_FIXED_POINT_NUMBER_H
|
#endif // FIXED_POINT_NUMBER_HPP
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,7 +25,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "HilbertValue.h"
|
#include "hilbert_value.hpp"
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
#include <osrm/Coordinate.h>
|
||||||
|
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef HILBERTVALUE_H_
|
#ifndef HILBERT_VALUE_HPP
|
||||||
#define HILBERTVALUE_H_
|
#define HILBERT_VALUE_HPP
|
||||||
|
|
||||||
#include <cstdint>
|
#include <cstdint>
|
||||||
|
|
||||||
@@ -46,4 +46,4 @@ class HilbertCode
|
|||||||
inline void TransposeCoordinate(uint32_t *X) const;
|
inline void TransposeCoordinate(uint32_t *X) const;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* HILBERTVALUE_H_ */
|
#endif /* HILBERT_VALUE_HPP */
|
||||||
@@ -25,7 +25,7 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#include "ImportEdge.h"
|
#include "import_edge.hpp"
|
||||||
|
|
||||||
#include <boost/assert.hpp>
|
#include <boost/assert.hpp>
|
||||||
|
|
||||||
@@ -25,10 +25,10 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef IMPORT_EDGE_H
|
#ifndef IMPORT_EDGE_HPP
|
||||||
#define IMPORT_EDGE_H
|
#define IMPORT_EDGE_HPP
|
||||||
|
|
||||||
#include "../DataStructures/TravelMode.h"
|
#include "../data_structures/travel_mode.hpp"
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|
||||||
struct NodeBasedEdge
|
struct NodeBasedEdge
|
||||||
@@ -88,4 +88,4 @@ struct EdgeBasedEdge
|
|||||||
|
|
||||||
using ImportEdge = NodeBasedEdge;
|
using ImportEdge = NodeBasedEdge;
|
||||||
|
|
||||||
#endif /* IMPORT_EDGE_H */
|
#endif /* IMPORT_EDGE_HPP */
|
||||||
@@ -25,43 +25,70 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef BASEPARSER_H_
|
// based on
|
||||||
#define BASEPARSER_H_
|
// https://svn.apache.org/repos/asf/mesos/tags/release-0.9.0-incubating-RC0/src/common/json.hpp
|
||||||
|
|
||||||
#include <string>
|
#ifndef JSON_CONTAINER_H
|
||||||
|
#define JSON_CONTAINER_H
|
||||||
|
|
||||||
|
#include <variant/variant.hpp>
|
||||||
|
|
||||||
|
#include <iostream>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
#include <string>
|
||||||
|
#include <unordered_map>
|
||||||
|
|
||||||
struct lua_State;
|
namespace JSON
|
||||||
class ExtractorCallbacks;
|
|
||||||
class ScriptingEnvironment;
|
|
||||||
struct ExtractionWay;
|
|
||||||
struct ImportNode;
|
|
||||||
|
|
||||||
class BaseParser
|
|
||||||
{
|
{
|
||||||
public:
|
|
||||||
BaseParser() = delete;
|
|
||||||
BaseParser(const BaseParser &) = delete;
|
|
||||||
BaseParser(ExtractorCallbacks *extractor_callbacks,
|
|
||||||
ScriptingEnvironment &scripting_environment);
|
|
||||||
virtual ~BaseParser() {}
|
|
||||||
virtual bool ReadHeader() = 0;
|
|
||||||
virtual bool Parse() = 0;
|
|
||||||
|
|
||||||
virtual void ParseNodeInLua(ImportNode &node, lua_State *lua_state);
|
struct Object;
|
||||||
virtual void ParseWayInLua(ExtractionWay &way, lua_State *lua_state);
|
struct Array;
|
||||||
virtual void report_errors(lua_State *lua_state, const int status) const;
|
|
||||||
|
|
||||||
protected:
|
struct String
|
||||||
virtual void ReadUseRestrictionsSetting();
|
{
|
||||||
virtual void ReadRestrictionExceptions();
|
String() {}
|
||||||
virtual bool ShouldIgnoreRestriction(const std::string &except_tag_string) const;
|
String(const char *value) : value(value) {}
|
||||||
|
String(const std::string &value) : value(value) {}
|
||||||
ExtractorCallbacks *extractor_callbacks;
|
std::string value;
|
||||||
lua_State *lua_state;
|
|
||||||
ScriptingEnvironment &scripting_environment;
|
|
||||||
std::vector<std::string> restriction_exceptions;
|
|
||||||
bool use_turn_restrictions;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* BASEPARSER_H_ */
|
struct Number
|
||||||
|
{
|
||||||
|
Number() {}
|
||||||
|
Number(double value) : value(static_cast<double>(value)) {}
|
||||||
|
double value;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct True
|
||||||
|
{
|
||||||
|
};
|
||||||
|
|
||||||
|
struct False
|
||||||
|
{
|
||||||
|
};
|
||||||
|
|
||||||
|
struct Null
|
||||||
|
{
|
||||||
|
};
|
||||||
|
|
||||||
|
using Value = mapbox::util::variant<String,
|
||||||
|
Number,
|
||||||
|
mapbox::util::recursive_wrapper<Object>,
|
||||||
|
mapbox::util::recursive_wrapper<Array>,
|
||||||
|
True,
|
||||||
|
False,
|
||||||
|
Null>;
|
||||||
|
|
||||||
|
struct Object
|
||||||
|
{
|
||||||
|
std::unordered_map<std::string, Value> values;
|
||||||
|
};
|
||||||
|
|
||||||
|
struct Array
|
||||||
|
{
|
||||||
|
std::vector<Value> values;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace JSON
|
||||||
|
|
||||||
|
#endif // JSON_CONTAINER_H
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef LRUCACHE_H
|
#ifndef LRUCACHE_HPP
|
||||||
#define LRUCACHE_H
|
#define LRUCACHE_HPP
|
||||||
|
|
||||||
#include <list>
|
#include <list>
|
||||||
#include <unordered_map>
|
#include <unordered_map>
|
||||||
@@ -94,4 +94,4 @@ template <typename KeyT, typename ValueT> class LRUCache
|
|||||||
}
|
}
|
||||||
unsigned Size() const { return itemsInCache.size(); }
|
unsigned Size() const { return itemsInCache.size(); }
|
||||||
};
|
};
|
||||||
#endif // LRUCACHE_H
|
#endif // LRUCACHE_HPP
|
||||||
@@ -1,8 +1,35 @@
|
|||||||
#ifndef NODE_BASED_GRAPH_H_
|
/*
|
||||||
#define NODE_BASED_GRAPH_H_
|
|
||||||
|
|
||||||
#include "DynamicGraph.h"
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
#include "ImportEdge.h"
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef NODE_BASED_GRAPH_HPP
|
||||||
|
#define NODE_BASED_GRAPH_HPP
|
||||||
|
|
||||||
|
#include "dynamic_graph.hpp"
|
||||||
|
#include "import_edge.hpp"
|
||||||
#include "../Util/simple_logger.hpp"
|
#include "../Util/simple_logger.hpp"
|
||||||
|
|
||||||
#include <tbb/parallel_sort.h>
|
#include <tbb/parallel_sort.h>
|
||||||
@@ -241,4 +268,4 @@ SimpleNodeBasedDynamicGraphFromEdges(int number_of_nodes, std::vector<SimpleEdge
|
|||||||
return graph;
|
return graph;
|
||||||
}
|
}
|
||||||
|
|
||||||
#endif // NODE_BASED_GRAPH_H_
|
#endif // NODE_BASED_GRAPH_HPP
|
||||||
@@ -0,0 +1,41 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#ifndef NODE_ID_HPP
|
||||||
|
#define NODE_ID_HPP
|
||||||
|
|
||||||
|
#include "../typedefs.h"
|
||||||
|
|
||||||
|
struct Cmp
|
||||||
|
{
|
||||||
|
using value_type = NodeID;
|
||||||
|
bool operator()(const NodeID left, const NodeID right) const { return left < right; }
|
||||||
|
value_type max_value() { return 0xffffffff; }
|
||||||
|
value_type min_value() { return 0x0; }
|
||||||
|
};
|
||||||
|
|
||||||
|
#endif // NODE_ID_HPP
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,11 +25,11 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef ORIGINAL_EDGE_DATA_H
|
#ifndef ORIGINAL_EDGE_DATA_HPP
|
||||||
#define ORIGINAL_EDGE_DATA_H
|
#define ORIGINAL_EDGE_DATA_HPP
|
||||||
|
|
||||||
#include "TurnInstructions.h"
|
#include "travel_mode.hpp"
|
||||||
#include "../DataStructures/TravelMode.h"
|
#include "turn_instructions.hpp"
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|
||||||
#include <limits>
|
#include <limits>
|
||||||
@@ -61,4 +61,4 @@ struct OriginalEdgeData
|
|||||||
TravelMode travel_mode;
|
TravelMode travel_mode;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // ORIGINAL_EDGE_DATA_H
|
#endif // ORIGINAL_EDGE_DATA_HPP
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef PERCENT_H
|
#ifndef PERCENT_HPP
|
||||||
#define PERCENT_H
|
#define PERCENT_HPP
|
||||||
|
|
||||||
#include <iostream>
|
#include <iostream>
|
||||||
#include <atomic>
|
#include <atomic>
|
||||||
@@ -98,4 +98,4 @@ class Percent
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // PERCENT_H
|
#endif // PERCENT_HPP
|
||||||
@@ -0,0 +1,117 @@
|
|||||||
|
/*
|
||||||
|
|
||||||
|
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
||||||
|
All rights reserved.
|
||||||
|
|
||||||
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
|
are permitted provided that the following conditions are met:
|
||||||
|
|
||||||
|
Redistributions of source code must retain the above copyright notice, this list
|
||||||
|
of conditions and the following disclaimer.
|
||||||
|
Redistributions in binary form must reproduce the above copyright notice, this
|
||||||
|
list of conditions and the following disclaimer in the documentation and/or
|
||||||
|
other materials provided with the distribution.
|
||||||
|
|
||||||
|
THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
|
||||||
|
ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
|
||||||
|
WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
|
||||||
|
DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE FOR
|
||||||
|
ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
|
||||||
|
(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
|
||||||
|
LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
|
||||||
|
ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
|
||||||
|
(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
|
||||||
|
SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
||||||
|
|
||||||
|
*/
|
||||||
|
|
||||||
|
#include "phantom_node.hpp"
|
||||||
|
|
||||||
|
PhantomNode::PhantomNode(NodeID forward_node_id, NodeID reverse_node_id, unsigned name_id,
|
||||||
|
int forward_weight, int reverse_weight, int forward_offset, int reverse_offset,
|
||||||
|
unsigned packed_geometry_id, FixedPointCoordinate &location,
|
||||||
|
unsigned short fwd_segment_position,
|
||||||
|
TravelMode forward_travel_mode, TravelMode backward_travel_mode) :
|
||||||
|
forward_node_id(forward_node_id),
|
||||||
|
reverse_node_id(reverse_node_id),
|
||||||
|
name_id(name_id),
|
||||||
|
forward_weight(forward_weight),
|
||||||
|
reverse_weight(reverse_weight),
|
||||||
|
forward_offset(forward_offset),
|
||||||
|
reverse_offset(reverse_offset),
|
||||||
|
packed_geometry_id(packed_geometry_id),
|
||||||
|
location(location),
|
||||||
|
fwd_segment_position(fwd_segment_position),
|
||||||
|
forward_travel_mode(forward_travel_mode),
|
||||||
|
backward_travel_mode(backward_travel_mode)
|
||||||
|
{ }
|
||||||
|
|
||||||
|
PhantomNode::PhantomNode() :
|
||||||
|
forward_node_id(SPECIAL_NODEID),
|
||||||
|
reverse_node_id(SPECIAL_NODEID),
|
||||||
|
name_id(std::numeric_limits<unsigned>::max()),
|
||||||
|
forward_weight(INVALID_EDGE_WEIGHT),
|
||||||
|
reverse_weight(INVALID_EDGE_WEIGHT),
|
||||||
|
forward_offset(0),
|
||||||
|
reverse_offset(0),
|
||||||
|
packed_geometry_id(SPECIAL_EDGEID),
|
||||||
|
fwd_segment_position(0),
|
||||||
|
forward_travel_mode(TRAVEL_MODE_INACCESSIBLE),
|
||||||
|
backward_travel_mode(TRAVEL_MODE_INACCESSIBLE)
|
||||||
|
{ }
|
||||||
|
|
||||||
|
int PhantomNode::GetForwardWeightPlusOffset() const
|
||||||
|
{
|
||||||
|
if (SPECIAL_NODEID == forward_node_id)
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
return forward_offset + forward_weight;
|
||||||
|
}
|
||||||
|
|
||||||
|
int PhantomNode::GetReverseWeightPlusOffset() const
|
||||||
|
{
|
||||||
|
if (SPECIAL_NODEID == reverse_node_id)
|
||||||
|
{
|
||||||
|
return 0;
|
||||||
|
}
|
||||||
|
return reverse_offset + reverse_weight;
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PhantomNode::is_bidirected() const
|
||||||
|
{
|
||||||
|
return (forward_node_id != SPECIAL_NODEID) &&
|
||||||
|
(reverse_node_id != SPECIAL_NODEID);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PhantomNode::is_compressed() const
|
||||||
|
{
|
||||||
|
return (forward_offset != 0) || (reverse_offset != 0);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PhantomNode::is_valid(const unsigned number_of_nodes) const
|
||||||
|
{
|
||||||
|
return
|
||||||
|
location.is_valid() &&
|
||||||
|
(
|
||||||
|
(forward_node_id < number_of_nodes) ||
|
||||||
|
(reverse_node_id < number_of_nodes)
|
||||||
|
) &&
|
||||||
|
(
|
||||||
|
(forward_weight != INVALID_EDGE_WEIGHT) ||
|
||||||
|
(reverse_weight != INVALID_EDGE_WEIGHT)
|
||||||
|
) &&
|
||||||
|
(name_id != INVALID_NAMEID
|
||||||
|
);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PhantomNode::is_valid() const
|
||||||
|
{
|
||||||
|
return location.is_valid() &&
|
||||||
|
(name_id != INVALID_NAMEID);
|
||||||
|
}
|
||||||
|
|
||||||
|
bool PhantomNode::operator==(const PhantomNode & other) const
|
||||||
|
{
|
||||||
|
return location == other.location;
|
||||||
|
}
|
||||||
@@ -29,10 +29,10 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
#define PHANTOM_NODES_H
|
#define PHANTOM_NODES_H
|
||||||
|
|
||||||
#include <osrm/Coordinate.h>
|
#include <osrm/Coordinate.h>
|
||||||
#include "../DataStructures/TravelMode.h"
|
#include "../data_structures/travel_mode.hpp"
|
||||||
#include "../Util/simple_logger.hpp"
|
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|
||||||
|
#include <iostream>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
struct PhantomNode
|
struct PhantomNode
|
||||||
@@ -41,34 +41,9 @@ struct PhantomNode
|
|||||||
int forward_weight, int reverse_weight, int forward_offset, int reverse_offset,
|
int forward_weight, int reverse_weight, int forward_offset, int reverse_offset,
|
||||||
unsigned packed_geometry_id, FixedPointCoordinate &location,
|
unsigned packed_geometry_id, FixedPointCoordinate &location,
|
||||||
unsigned short fwd_segment_position,
|
unsigned short fwd_segment_position,
|
||||||
TravelMode forward_travel_mode, TravelMode backward_travel_mode) :
|
TravelMode forward_travel_mode, TravelMode backward_travel_mode);
|
||||||
forward_node_id(forward_node_id),
|
|
||||||
reverse_node_id(reverse_node_id),
|
|
||||||
name_id(name_id),
|
|
||||||
forward_weight(forward_weight),
|
|
||||||
reverse_weight(reverse_weight),
|
|
||||||
forward_offset(forward_offset),
|
|
||||||
reverse_offset(reverse_offset),
|
|
||||||
packed_geometry_id(packed_geometry_id),
|
|
||||||
location(location),
|
|
||||||
fwd_segment_position(fwd_segment_position),
|
|
||||||
forward_travel_mode(forward_travel_mode),
|
|
||||||
backward_travel_mode(backward_travel_mode)
|
|
||||||
{ }
|
|
||||||
|
|
||||||
PhantomNode() :
|
PhantomNode();
|
||||||
forward_node_id(SPECIAL_NODEID),
|
|
||||||
reverse_node_id(SPECIAL_NODEID),
|
|
||||||
name_id(std::numeric_limits<unsigned>::max()),
|
|
||||||
forward_weight(INVALID_EDGE_WEIGHT),
|
|
||||||
reverse_weight(INVALID_EDGE_WEIGHT),
|
|
||||||
forward_offset(0),
|
|
||||||
reverse_offset(0),
|
|
||||||
packed_geometry_id(SPECIAL_EDGEID),
|
|
||||||
fwd_segment_position(0),
|
|
||||||
forward_travel_mode(TRAVEL_MODE_INACCESSIBLE),
|
|
||||||
backward_travel_mode(TRAVEL_MODE_INACCESSIBLE)
|
|
||||||
{ }
|
|
||||||
|
|
||||||
NodeID forward_node_id;
|
NodeID forward_node_id;
|
||||||
NodeID reverse_node_id;
|
NodeID reverse_node_id;
|
||||||
@@ -83,63 +58,19 @@ struct PhantomNode
|
|||||||
TravelMode forward_travel_mode : 4;
|
TravelMode forward_travel_mode : 4;
|
||||||
TravelMode backward_travel_mode : 4;
|
TravelMode backward_travel_mode : 4;
|
||||||
|
|
||||||
int GetForwardWeightPlusOffset() const
|
int GetForwardWeightPlusOffset() const;
|
||||||
{
|
|
||||||
if (SPECIAL_NODEID == forward_node_id)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
const int result = (forward_offset + forward_weight);
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
int GetReverseWeightPlusOffset() const
|
int GetReverseWeightPlusOffset() const;
|
||||||
{
|
|
||||||
if (SPECIAL_NODEID == reverse_node_id)
|
|
||||||
{
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
const int result = (reverse_offset + reverse_weight);
|
|
||||||
return result;
|
|
||||||
}
|
|
||||||
|
|
||||||
bool isBidirected() const
|
bool is_bidirected() const;
|
||||||
{
|
|
||||||
return (forward_node_id != SPECIAL_NODEID) &&
|
|
||||||
(reverse_node_id != SPECIAL_NODEID);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool IsCompressed() const
|
bool is_compressed() const;
|
||||||
{
|
|
||||||
return (forward_offset != 0) || (reverse_offset != 0);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool isValid(const unsigned numberOfNodes) const
|
bool is_valid(const unsigned numberOfNodes) const;
|
||||||
{
|
|
||||||
return
|
|
||||||
location.isValid() &&
|
|
||||||
(
|
|
||||||
(forward_node_id < numberOfNodes) ||
|
|
||||||
(reverse_node_id < numberOfNodes)
|
|
||||||
) &&
|
|
||||||
(
|
|
||||||
(forward_weight != INVALID_EDGE_WEIGHT) ||
|
|
||||||
(reverse_weight != INVALID_EDGE_WEIGHT)
|
|
||||||
) &&
|
|
||||||
(name_id != std::numeric_limits<unsigned>::max()
|
|
||||||
);
|
|
||||||
}
|
|
||||||
|
|
||||||
bool isValid() const
|
bool is_valid() const;
|
||||||
{
|
|
||||||
return location.isValid() &&
|
|
||||||
(name_id != std::numeric_limits<unsigned>::max());
|
|
||||||
}
|
|
||||||
|
|
||||||
bool operator==(const PhantomNode & other) const
|
bool operator==(const PhantomNode & other) const;
|
||||||
{
|
|
||||||
return location == other.location;
|
|
||||||
}
|
|
||||||
};
|
};
|
||||||
|
|
||||||
using PhantomNodeArray = std::vector<std::vector<PhantomNode>>;
|
using PhantomNodeArray = std::vector<std::vector<PhantomNode>>;
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef QUERYEDGE_H_
|
#ifndef QUERYEDGE_HPP_
|
||||||
#define QUERYEDGE_H_
|
#define QUERYEDGE_HPP_
|
||||||
|
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|
||||||
@@ -78,4 +78,4 @@ struct QueryEdge
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif /* QUERYEDGE_H_ */
|
#endif /* QUERYEDGE_HPP_ */
|
||||||
@@ -1,6 +1,6 @@
|
|||||||
/*
|
/*
|
||||||
|
|
||||||
Copyright (c) 2013, Project OSRM, Dennis Luxen, others
|
Copyright (c) 2014, Project OSRM, Dennis Luxen, others
|
||||||
All rights reserved.
|
All rights reserved.
|
||||||
|
|
||||||
Redistribution and use in source and binary forms, with or without modification,
|
Redistribution and use in source and binary forms, with or without modification,
|
||||||
@@ -25,8 +25,8 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
*/
|
*/
|
||||||
|
|
||||||
#ifndef QUERY_NODE_H
|
#ifndef QUERY_NODE_HPP
|
||||||
#define QUERY_NODE_H
|
#define QUERY_NODE_HPP
|
||||||
|
|
||||||
#include "../typedefs.h"
|
#include "../typedefs.h"
|
||||||
|
|
||||||
@@ -36,13 +36,13 @@ SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
|
|||||||
|
|
||||||
#include <limits>
|
#include <limits>
|
||||||
|
|
||||||
struct NodeInfo
|
struct QueryNode
|
||||||
{
|
{
|
||||||
using key_type = NodeID; // type of NodeID
|
using key_type = NodeID; // type of NodeID
|
||||||
using value_type = int; // type of lat,lons
|
using value_type = int; // type of lat,lons
|
||||||
|
|
||||||
explicit NodeInfo(int lat, int lon, NodeID node_id) : lat(lat), lon(lon), node_id(node_id) {}
|
explicit QueryNode(int lat, int lon, NodeID node_id) : lat(lat), lon(lon), node_id(node_id) {}
|
||||||
NodeInfo()
|
QueryNode()
|
||||||
: lat(std::numeric_limits<int>::max()), lon(std::numeric_limits<int>::max()),
|
: lat(std::numeric_limits<int>::max()), lon(std::numeric_limits<int>::max()),
|
||||||
node_id(std::numeric_limits<unsigned>::max())
|
node_id(std::numeric_limits<unsigned>::max())
|
||||||
{
|
{
|
||||||
@@ -52,16 +52,16 @@ struct NodeInfo
|
|||||||
int lon;
|
int lon;
|
||||||
NodeID node_id;
|
NodeID node_id;
|
||||||
|
|
||||||
static NodeInfo min_value()
|
static QueryNode min_value()
|
||||||
{
|
{
|
||||||
return NodeInfo(static_cast<int>(-90 * COORDINATE_PRECISION),
|
return QueryNode(static_cast<int>(-90 * COORDINATE_PRECISION),
|
||||||
static_cast<int>(-180 * COORDINATE_PRECISION),
|
static_cast<int>(-180 * COORDINATE_PRECISION),
|
||||||
std::numeric_limits<NodeID>::min());
|
std::numeric_limits<NodeID>::min());
|
||||||
}
|
}
|
||||||
|
|
||||||
static NodeInfo max_value()
|
static QueryNode max_value()
|
||||||
{
|
{
|
||||||
return NodeInfo(static_cast<int>(90 * COORDINATE_PRECISION),
|
return QueryNode(static_cast<int>(90 * COORDINATE_PRECISION),
|
||||||
static_cast<int>(180 * COORDINATE_PRECISION),
|
static_cast<int>(180 * COORDINATE_PRECISION),
|
||||||
std::numeric_limits<NodeID>::max());
|
std::numeric_limits<NodeID>::max());
|
||||||
}
|
}
|
||||||
@@ -82,4 +82,4 @@ struct NodeInfo
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // QUERY_NODE_H
|
#endif // QUERY_NODE_HPP
|
||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user