Support rectangular matrix with less sources than targets
This commit is contained in:
parent
4253ebf243
commit
478d4a571a
@ -148,8 +148,18 @@ void RouteParameters::addCoordinate(
|
|||||||
static_cast<int>(COORDINATE_PRECISION * boost::fusion::at_c<1>(received_coordinates)));
|
static_cast<int>(COORDINATE_PRECISION * boost::fusion::at_c<1>(received_coordinates)));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void RouteParameters::addSource(
|
||||||
|
const boost::fusion::vector<double, double> &received_coordinates)
|
||||||
|
{
|
||||||
|
sources.emplace_back(
|
||||||
|
static_cast<int>(COORDINATE_PRECISION * boost::fusion::at_c<0>(received_coordinates)),
|
||||||
|
static_cast<int>(COORDINATE_PRECISION * boost::fusion::at_c<1>(received_coordinates)));
|
||||||
|
}
|
||||||
|
|
||||||
void RouteParameters::getCoordinatesFromGeometry(const std::string &geometry_string)
|
void RouteParameters::getCoordinatesFromGeometry(const std::string &geometry_string)
|
||||||
{
|
{
|
||||||
PolylineCompressor pc;
|
PolylineCompressor pc;
|
||||||
coordinates = pc.decode_string(geometry_string);
|
coordinates = pc.decode_string(geometry_string);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
void RouteParameters::setMappedPointsFlag(const bool flag) { mapped_points = flag; }
|
||||||
|
@ -1,5 +1,4 @@
|
|||||||
When /^I request a travel time matrix I should get$/ do |table|
|
When /^I request a travel time matrix I should get$/ do |table|
|
||||||
|
|
||||||
no_route = 2147483647 # MAX_INT
|
no_route = 2147483647 # MAX_INT
|
||||||
|
|
||||||
raise "*** Top-left cell of matrix table must be empty" unless table.headers[0]==""
|
raise "*** Top-left cell of matrix table must be empty" unless table.headers[0]==""
|
||||||
@ -7,7 +6,7 @@ When /^I request a travel time matrix I should get$/ do |table|
|
|||||||
nodes = []
|
nodes = []
|
||||||
column_headers = table.headers[1..-1]
|
column_headers = table.headers[1..-1]
|
||||||
row_headers = table.rows.map { |h| h.first }
|
row_headers = table.rows.map { |h| h.first }
|
||||||
unless column_headers==row_headers
|
unless column_headers==row_headers || @query_params['src']
|
||||||
raise "*** Column and row headers must match in matrix table, got #{column_headers.inspect} and #{row_headers.inspect}"
|
raise "*** Column and row headers must match in matrix table, got #{column_headers.inspect} and #{row_headers.inspect}"
|
||||||
end
|
end
|
||||||
column_headers.each do |node_name|
|
column_headers.each do |node_name|
|
||||||
@ -23,6 +22,10 @@ When /^I request a travel time matrix I should get$/ do |table|
|
|||||||
|
|
||||||
# compute matrix
|
# compute matrix
|
||||||
params = @query_params
|
params = @query_params
|
||||||
|
if params['src']
|
||||||
|
node = find_node_by_name(params['src'])
|
||||||
|
params['src'] = node.lat + ',' + node.lon
|
||||||
|
end
|
||||||
response = request_table nodes, params
|
response = request_table nodes, params
|
||||||
if response.body.empty? == false
|
if response.body.empty? == false
|
||||||
json = JSON.parse response.body
|
json = JSON.parse response.body
|
||||||
|
@ -100,3 +100,24 @@ Feature: Basic Distance Matrix
|
|||||||
| y | 500 | 0 | 300 | 200 |
|
| y | 500 | 0 | 300 | 200 |
|
||||||
| d | 200 | 300 | 0 | 300 |
|
| d | 200 | 300 | 0 | 300 |
|
||||||
| e | 300 | 400 | 100 | 0 |
|
| e | 300 | 400 | 100 | 0 |
|
||||||
|
|
||||||
|
Scenario: Testbot - Travel time matrix and mapped coordinates with only one source
|
||||||
|
Given the node map
|
||||||
|
| a | b | c |
|
||||||
|
| d | e | f |
|
||||||
|
|
||||||
|
And the ways
|
||||||
|
| nodes |
|
||||||
|
| abc |
|
||||||
|
| def |
|
||||||
|
| ad |
|
||||||
|
| be |
|
||||||
|
| cf |
|
||||||
|
|
||||||
|
And the query options
|
||||||
|
| mapped_points | true |
|
||||||
|
| src | a |
|
||||||
|
|
||||||
|
When I request a travel time matrix I should get
|
||||||
|
| | a | b | e | f |
|
||||||
|
| a | 0 | 100 | 200 | 300 |
|
||||||
|
@ -82,8 +82,12 @@ struct RouteParameters
|
|||||||
|
|
||||||
void addCoordinate(const boost::fusion::vector<double, double> &received_coordinates);
|
void addCoordinate(const boost::fusion::vector<double, double> &received_coordinates);
|
||||||
|
|
||||||
|
void addSource(const boost::fusion::vector<double, double> &received_coordinates);
|
||||||
|
|
||||||
void getCoordinatesFromGeometry(const std::string &geometry_string);
|
void getCoordinatesFromGeometry(const std::string &geometry_string);
|
||||||
|
|
||||||
|
void setMappedPointsFlag(const bool flag);
|
||||||
|
|
||||||
short zoom_level;
|
short zoom_level;
|
||||||
bool print_instructions;
|
bool print_instructions;
|
||||||
bool alternate_route;
|
bool alternate_route;
|
||||||
@ -92,6 +96,7 @@ struct RouteParameters
|
|||||||
bool deprecatedAPI;
|
bool deprecatedAPI;
|
||||||
bool uturn_default;
|
bool uturn_default;
|
||||||
bool classify;
|
bool classify;
|
||||||
|
bool mapped_points;
|
||||||
double matching_beta;
|
double matching_beta;
|
||||||
double gps_precision;
|
double gps_precision;
|
||||||
unsigned check_sum;
|
unsigned check_sum;
|
||||||
@ -105,6 +110,7 @@ struct RouteParameters
|
|||||||
std::vector<std::pair<const int,const boost::optional<int>>> bearings;
|
std::vector<std::pair<const int,const boost::optional<int>>> bearings;
|
||||||
std::vector<bool> uturns;
|
std::vector<bool> uturns;
|
||||||
std::vector<FixedPointCoordinate> coordinates;
|
std::vector<FixedPointCoordinate> coordinates;
|
||||||
|
std::vector<FixedPointCoordinate> sources;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // ROUTE_PARAMETERS_HPP
|
#endif // ROUTE_PARAMETERS_HPP
|
||||||
|
@ -70,13 +70,14 @@ template <class DataFacadeT> class DistanceTablePlugin final : public BasePlugin
|
|||||||
int HandleRequest(const RouteParameters &route_parameters,
|
int HandleRequest(const RouteParameters &route_parameters,
|
||||||
osrm::json::Object &json_result) override final
|
osrm::json::Object &json_result) override final
|
||||||
{
|
{
|
||||||
if (!check_all_coordinates(route_parameters.coordinates))
|
if (!check_all_coordinates(route_parameters.coordinates) ||
|
||||||
|
(route_parameters.sources.size() && !check_all_coordinates(route_parameters.sources, 1)))
|
||||||
{
|
{
|
||||||
return 400;
|
return 400;
|
||||||
}
|
}
|
||||||
|
|
||||||
const auto &input_bearings = route_parameters.bearings;
|
const auto &input_bearings = route_parameters.bearings;
|
||||||
if (input_bearings.size() > 0 && route_parameters.coordinates.size() != input_bearings.size())
|
if (input_bearings.size() > 0 && route_parameters.coordinates.size() + route_parameters.sources.size() != input_bearings.size())
|
||||||
{
|
{
|
||||||
json_result.values["status"] = "Number of bearings does not match number of coordinates .";
|
json_result.values["status"] = "Number of bearings does not match number of coordinates .";
|
||||||
return 400;
|
return 400;
|
||||||
@ -87,7 +88,7 @@ template <class DataFacadeT> class DistanceTablePlugin final : public BasePlugin
|
|||||||
std::min(static_cast<unsigned>(max_locations_distance_table),
|
std::min(static_cast<unsigned>(max_locations_distance_table),
|
||||||
static_cast<unsigned>(route_parameters.coordinates.size()));
|
static_cast<unsigned>(route_parameters.coordinates.size()));
|
||||||
|
|
||||||
PhantomNodeArray phantom_node_vector(max_locations);
|
PhantomNodeArray phantom_node_target_vector(max_locations);
|
||||||
for (const auto i : osrm::irange(0u, max_locations))
|
for (const auto i : osrm::irange(0u, max_locations))
|
||||||
{
|
{
|
||||||
if (checksum_OK && i < route_parameters.hints.size() &&
|
if (checksum_OK && i < route_parameters.hints.size() &&
|
||||||
@ -97,21 +98,49 @@ template <class DataFacadeT> class DistanceTablePlugin final : public BasePlugin
|
|||||||
ObjectEncoder::DecodeFromBase64(route_parameters.hints[i], current_phantom_node);
|
ObjectEncoder::DecodeFromBase64(route_parameters.hints[i], current_phantom_node);
|
||||||
if (current_phantom_node.is_valid(facade->GetNumberOfNodes()))
|
if (current_phantom_node.is_valid(facade->GetNumberOfNodes()))
|
||||||
{
|
{
|
||||||
phantom_node_vector[i].emplace_back(std::move(current_phantom_node));
|
phantom_node_target_vector[i].emplace_back(std::move(current_phantom_node));
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
const int bearing = input_bearings.size() > 0 ? input_bearings[i].first : 0;
|
const int bearing = input_bearings.size() > 0 ? input_bearings[i].first : 0;
|
||||||
const int range = input_bearings.size() > 0 ? (input_bearings[i].second?*input_bearings[i].second:10) : 180;
|
const int range = input_bearings.size() > 0 ? (input_bearings[i].second?*input_bearings[i].second:10) : 180;
|
||||||
facade->IncrementalFindPhantomNodeForCoordinate(route_parameters.coordinates[i],
|
facade->IncrementalFindPhantomNodeForCoordinate(route_parameters.coordinates[i],
|
||||||
phantom_node_vector[i], 1, bearing, range);
|
phantom_node_target_vector[i], 1, bearing, range);
|
||||||
|
|
||||||
BOOST_ASSERT(phantom_node_vector[i].front().is_valid(facade->GetNumberOfNodes()));
|
BOOST_ASSERT(phantom_node_target_vector[i].front().is_valid(facade->GetNumberOfNodes()));
|
||||||
|
}
|
||||||
|
unsigned nb_coordinates = route_parameters.coordinates.size();
|
||||||
|
max_locations = 0;
|
||||||
|
if (route_parameters.sources.size())
|
||||||
|
{
|
||||||
|
max_locations = std::min(static_cast<unsigned>(max_locations_distance_table),
|
||||||
|
static_cast<unsigned>(route_parameters.sources.size()));
|
||||||
|
}
|
||||||
|
PhantomNodeArray phantom_node_source_vector(max_locations);
|
||||||
|
for (const auto i : osrm::irange(0u, max_locations))
|
||||||
|
{
|
||||||
|
if (checksum_OK && i < route_parameters.hints.size() - route_parameters.coordinates.size() &&
|
||||||
|
!route_parameters.hints[i+route_parameters.coordinates.size()].empty())
|
||||||
|
{
|
||||||
|
PhantomNode current_phantom_node;
|
||||||
|
ObjectEncoder::DecodeFromBase64(route_parameters.hints[i+route_parameters.coordinates.size()], current_phantom_node);
|
||||||
|
if (current_phantom_node.is_valid(facade->GetNumberOfNodes()))
|
||||||
|
{
|
||||||
|
phantom_node_source_vector[i].emplace_back(std::move(current_phantom_node));
|
||||||
|
continue;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
const int bearing = input_bearings.size() > 0 ? input_bearings[nb_coordinates + i].first : 0;
|
||||||
|
const int range = input_bearings.size() > 0 ? (input_bearings[nb_coordinates + i].second?*input_bearings[nb_coordinates + i].second:10) : 180;
|
||||||
|
facade->IncrementalFindPhantomNodeForCoordinate(route_parameters.sources[i],
|
||||||
|
phantom_node_source_vector[i], 1, bearing, range);
|
||||||
|
|
||||||
|
BOOST_ASSERT(phantom_node_source_vector[i].front().is_valid(facade->GetNumberOfNodes()));
|
||||||
}
|
}
|
||||||
|
|
||||||
// TIMER_START(distance_table);
|
// TIMER_START(distance_table);
|
||||||
std::shared_ptr<std::vector<EdgeWeight>> result_table =
|
std::shared_ptr<std::vector<EdgeWeight>> result_table =
|
||||||
search_engine_ptr->distance_table(phantom_node_vector);
|
search_engine_ptr->distance_table(phantom_node_target_vector, phantom_node_source_vector);
|
||||||
// TIMER_STOP(distance_table);
|
// TIMER_STOP(distance_table);
|
||||||
|
|
||||||
if (!result_table)
|
if (!result_table)
|
||||||
@ -119,17 +148,41 @@ template <class DataFacadeT> class DistanceTablePlugin final : public BasePlugin
|
|||||||
return 400;
|
return 400;
|
||||||
}
|
}
|
||||||
|
|
||||||
osrm::json::Array json_array;
|
osrm::json::Array matrix_json_array;
|
||||||
const auto number_of_locations = phantom_node_vector.size();
|
const auto number_of_targets = phantom_node_target_vector.size();
|
||||||
for (const auto row : osrm::irange<std::size_t>(0, number_of_locations))
|
const auto number_of_sources = (phantom_node_source_vector.size()) ? phantom_node_source_vector.size() : number_of_targets;
|
||||||
|
for (const auto row : osrm::irange<std::size_t>(0, number_of_sources))
|
||||||
{
|
{
|
||||||
osrm::json::Array json_row;
|
osrm::json::Array json_row;
|
||||||
auto row_begin_iterator = result_table->begin() + (row * number_of_locations);
|
auto row_begin_iterator = result_table->begin() + (row * number_of_targets);
|
||||||
auto row_end_iterator = result_table->begin() + ((row + 1) * number_of_locations);
|
auto row_end_iterator = result_table->begin() + ((row + 1) * number_of_targets);
|
||||||
json_row.values.insert(json_row.values.end(), row_begin_iterator, row_end_iterator);
|
json_row.values.insert(json_row.values.end(), row_begin_iterator, row_end_iterator);
|
||||||
json_array.values.push_back(json_row);
|
matrix_json_array.values.push_back(json_row);
|
||||||
|
}
|
||||||
|
json_result.values["distance_table"] = matrix_json_array;
|
||||||
|
if (route_parameters.mapped_points) {
|
||||||
|
osrm::json::Array target_coord_json_array;
|
||||||
|
for (const std::vector<PhantomNode> &phantom_node_vector : phantom_node_target_vector)
|
||||||
|
{
|
||||||
|
osrm::json::Array json_coord;
|
||||||
|
FixedPointCoordinate coord = phantom_node_vector[0].location;
|
||||||
|
json_coord.values.push_back(coord.lat / COORDINATE_PRECISION);
|
||||||
|
json_coord.values.push_back(coord.lon / COORDINATE_PRECISION);
|
||||||
|
target_coord_json_array.values.push_back(json_coord);
|
||||||
|
}
|
||||||
|
json_result.values["target_mapped_coordinates"] = target_coord_json_array;
|
||||||
|
osrm::json::Array source_coord_json_array;
|
||||||
|
for (const std::vector<PhantomNode> &phantom_node_vector : phantom_node_source_vector)
|
||||||
|
{
|
||||||
|
osrm::json::Array json_coord;
|
||||||
|
FixedPointCoordinate coord = phantom_node_vector[0].location;
|
||||||
|
json_coord.values.push_back(coord.lat / COORDINATE_PRECISION);
|
||||||
|
json_coord.values.push_back(coord.lon / COORDINATE_PRECISION);
|
||||||
|
source_coord_json_array.values.push_back(json_coord);
|
||||||
|
}
|
||||||
|
if (source_coord_json_array.values.size())
|
||||||
|
json_result.values["source_mapped_coordinates"] = source_coord_json_array;
|
||||||
}
|
}
|
||||||
json_result.values["distance_table"] = json_array;
|
|
||||||
// osrm::json::render(reply.content, json_object);
|
// osrm::json::render(reply.content, json_object);
|
||||||
return 200;
|
return 200;
|
||||||
}
|
}
|
||||||
|
@ -45,9 +45,9 @@ class BasePlugin
|
|||||||
virtual const std::string GetDescriptor() const = 0;
|
virtual const std::string GetDescriptor() const = 0;
|
||||||
virtual int HandleRequest(const RouteParameters &, osrm::json::Object &) = 0;
|
virtual int HandleRequest(const RouteParameters &, osrm::json::Object &) = 0;
|
||||||
virtual bool
|
virtual bool
|
||||||
check_all_coordinates(const std::vector<FixedPointCoordinate> &coordinates) const final
|
check_all_coordinates(const std::vector<FixedPointCoordinate> &coordinates, const unsigned min = 2) const final
|
||||||
{
|
{
|
||||||
if (2 > coordinates.size() || std::any_of(std::begin(coordinates), std::end(coordinates),
|
if (min > coordinates.size() || std::any_of(std::begin(coordinates), std::end(coordinates),
|
||||||
[](const FixedPointCoordinate &coordinate)
|
[](const FixedPointCoordinate &coordinate)
|
||||||
{
|
{
|
||||||
return !coordinate.is_valid();
|
return !coordinate.is_valid();
|
||||||
|
@ -67,11 +67,12 @@ class ManyToManyRouting final
|
|||||||
~ManyToManyRouting() {}
|
~ManyToManyRouting() {}
|
||||||
|
|
||||||
std::shared_ptr<std::vector<EdgeWeight>>
|
std::shared_ptr<std::vector<EdgeWeight>>
|
||||||
operator()(const PhantomNodeArray &phantom_nodes_array) const
|
operator()(const PhantomNodeArray &phantom_targets_array, const PhantomNodeArray &phantom_sources_array = PhantomNodeArray(0)) const
|
||||||
{
|
{
|
||||||
const auto number_of_locations = phantom_nodes_array.size();
|
const auto number_of_targets = phantom_targets_array.size();
|
||||||
|
const auto number_of_sources = (phantom_sources_array.size()) ? phantom_sources_array.size() : number_of_targets;
|
||||||
std::shared_ptr<std::vector<EdgeWeight>> result_table =
|
std::shared_ptr<std::vector<EdgeWeight>> result_table =
|
||||||
std::make_shared<std::vector<EdgeWeight>>(number_of_locations * number_of_locations,
|
std::make_shared<std::vector<EdgeWeight>>(number_of_targets * number_of_sources,
|
||||||
std::numeric_limits<EdgeWeight>::max());
|
std::numeric_limits<EdgeWeight>::max());
|
||||||
|
|
||||||
engine_working_data.InitializeOrClearFirstThreadLocalStorage(
|
engine_working_data.InitializeOrClearFirstThreadLocalStorage(
|
||||||
@ -82,7 +83,7 @@ class ManyToManyRouting final
|
|||||||
SearchSpaceWithBuckets search_space_with_buckets;
|
SearchSpaceWithBuckets search_space_with_buckets;
|
||||||
|
|
||||||
unsigned target_id = 0;
|
unsigned target_id = 0;
|
||||||
for (const std::vector<PhantomNode> &phantom_node_vector : phantom_nodes_array)
|
for (const std::vector<PhantomNode> &phantom_node_vector : phantom_targets_array)
|
||||||
{
|
{
|
||||||
query_heap.Clear();
|
query_heap.Clear();
|
||||||
// insert target(s) at distance 0
|
// insert target(s) at distance 0
|
||||||
@ -113,7 +114,7 @@ class ManyToManyRouting final
|
|||||||
|
|
||||||
// for each source do forward search
|
// for each source do forward search
|
||||||
unsigned source_id = 0;
|
unsigned source_id = 0;
|
||||||
for (const std::vector<PhantomNode> &phantom_node_vector : phantom_nodes_array)
|
for (const std::vector<PhantomNode> &phantom_node_vector : (phantom_sources_array.size() ? phantom_sources_array : phantom_targets_array))
|
||||||
{
|
{
|
||||||
query_heap.Clear();
|
query_heap.Clear();
|
||||||
for (const PhantomNode &phantom_node : phantom_node_vector)
|
for (const PhantomNode &phantom_node : phantom_node_vector)
|
||||||
@ -136,13 +137,13 @@ class ManyToManyRouting final
|
|||||||
// explore search space
|
// explore search space
|
||||||
while (!query_heap.Empty())
|
while (!query_heap.Empty())
|
||||||
{
|
{
|
||||||
ForwardRoutingStep(source_id, number_of_locations, query_heap,
|
ForwardRoutingStep(source_id, number_of_targets, query_heap,
|
||||||
search_space_with_buckets, result_table);
|
search_space_with_buckets, result_table);
|
||||||
}
|
}
|
||||||
|
|
||||||
++source_id;
|
++source_id;
|
||||||
}
|
}
|
||||||
BOOST_ASSERT(source_id == target_id);
|
// BOOST_ASSERT(source_id == target_id);
|
||||||
return result_table;
|
return result_table;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -40,9 +40,9 @@ template <typename Iterator, class HandlerT> struct APIGrammar : qi::grammar<Ite
|
|||||||
{
|
{
|
||||||
api_call = qi::lit('/') >> string[boost::bind(&HandlerT::setService, handler, ::_1)] >>
|
api_call = qi::lit('/') >> string[boost::bind(&HandlerT::setService, handler, ::_1)] >>
|
||||||
*(query) >> -(uturns);
|
*(query) >> -(uturns);
|
||||||
query = ('?') >> (+(zoom | output | jsonp | checksum | location | hint | timestamp | bearing | u | cmp |
|
query = ('?') >> (+(zoom | output | jsonp | checksum | location | source | hint | timestamp | bearing | u | cmp |
|
||||||
language | instruction | geometry | alt_route | old_API | num_results |
|
language | instruction | geometry | alt_route | old_API | num_results |
|
||||||
matching_beta | gps_precision | classify | locs));
|
matching_beta | gps_precision | classify | locs | mapped_points));
|
||||||
|
|
||||||
zoom = (-qi::lit('&')) >> qi::lit('z') >> '=' >>
|
zoom = (-qi::lit('&')) >> qi::lit('z') >> '=' >>
|
||||||
qi::short_[boost::bind(&HandlerT::setZoomLevel, handler, ::_1)];
|
qi::short_[boost::bind(&HandlerT::setZoomLevel, handler, ::_1)];
|
||||||
@ -61,6 +61,9 @@ template <typename Iterator, class HandlerT> struct APIGrammar : qi::grammar<Ite
|
|||||||
location = (-qi::lit('&')) >> qi::lit("loc") >> '=' >>
|
location = (-qi::lit('&')) >> qi::lit("loc") >> '=' >>
|
||||||
(qi::double_ >> qi::lit(',') >>
|
(qi::double_ >> qi::lit(',') >>
|
||||||
qi::double_)[boost::bind(&HandlerT::addCoordinate, handler, ::_1)];
|
qi::double_)[boost::bind(&HandlerT::addCoordinate, handler, ::_1)];
|
||||||
|
source = (-qi::lit('&')) >> qi::lit("src") >> '=' >>
|
||||||
|
(qi::double_ >> qi::lit(',') >>
|
||||||
|
qi::double_)[boost::bind(&HandlerT::addSource, handler, ::_1)];
|
||||||
hint = (-qi::lit('&')) >> qi::lit("hint") >> '=' >>
|
hint = (-qi::lit('&')) >> qi::lit("hint") >> '=' >>
|
||||||
stringwithDot[boost::bind(&HandlerT::addHint, handler, ::_1)];
|
stringwithDot[boost::bind(&HandlerT::addHint, handler, ::_1)];
|
||||||
timestamp = (-qi::lit('&')) >> qi::lit("t") >> '=' >>
|
timestamp = (-qi::lit('&')) >> qi::lit("t") >> '=' >>
|
||||||
@ -87,6 +90,8 @@ template <typename Iterator, class HandlerT> struct APIGrammar : qi::grammar<Ite
|
|||||||
qi::bool_[boost::bind(&HandlerT::setClassify, handler, ::_1)];
|
qi::bool_[boost::bind(&HandlerT::setClassify, handler, ::_1)];
|
||||||
locs = (-qi::lit('&')) >> qi::lit("locs") >> '=' >>
|
locs = (-qi::lit('&')) >> qi::lit("locs") >> '=' >>
|
||||||
stringforPolyline[boost::bind(&HandlerT::getCoordinatesFromGeometry, handler, ::_1)];
|
stringforPolyline[boost::bind(&HandlerT::getCoordinatesFromGeometry, handler, ::_1)];
|
||||||
|
mapped_points = (-qi::lit('&')) >> qi::lit("mapped_points") >> '=' >>
|
||||||
|
qi::bool_[boost::bind(&HandlerT::setMappedPointsFlag, handler, ::_1)];
|
||||||
|
|
||||||
string = +(qi::char_("a-zA-Z"));
|
string = +(qi::char_("a-zA-Z"));
|
||||||
stringwithDot = +(qi::char_("a-zA-Z0-9_.-"));
|
stringwithDot = +(qi::char_("a-zA-Z0-9_.-"));
|
||||||
@ -96,9 +101,9 @@ template <typename Iterator, class HandlerT> struct APIGrammar : qi::grammar<Ite
|
|||||||
}
|
}
|
||||||
|
|
||||||
qi::rule<Iterator> api_call, query;
|
qi::rule<Iterator> api_call, query;
|
||||||
qi::rule<Iterator, std::string()> service, zoom, output, string, jsonp, checksum, location,
|
qi::rule<Iterator, std::string()> service, zoom, output, string, jsonp, checksum, location, source,
|
||||||
hint, timestamp, bearing, stringwithDot, stringwithPercent, language, instruction, geometry, cmp, alt_route, u,
|
hint, timestamp, bearing, stringwithDot, stringwithPercent, language, instruction, geometry, cmp, alt_route, u,
|
||||||
uturns, old_API, num_results, matching_beta, gps_precision, classify, locs, stringforPolyline;
|
uturns, old_API, num_results, matching_beta, gps_precision, classify, locs, mapped_points, stringforPolyline;
|
||||||
|
|
||||||
HandlerT *handler;
|
HandlerT *handler;
|
||||||
};
|
};
|
||||||
|
Loading…
Reference in New Issue
Block a user