宁波一日游(调用高德开放平台)

2023-10-13 05:40

本文主要是介绍宁波一日游(调用高德开放平台),希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

旅行中总有需要优化的地方

  1. 按照什么顺序游玩在路上乘车的时间最短?
  2. 如何在固定的时间时长内浏览最多的景点?
  3. 晚上在哪住宿比较合适?(如果要住宿)

本文使用R语言调用高德开放平台模拟各种方案给出一个解决方案。

获取高德开放平台调用权限

我的应用 | 高德控制台

登陆自己的高德账号,创建新应用(随意选择类型),添加新的服务(选择Web服务即可),添加完成即可获得自己的【key】,该【key】会在之后用到。

获取旅游景点地理坐标

简单罗列几个宁波主城区观赏游玩的景点:月湖公园(包括天一阁、鼓楼)、宁波博物馆、南塘老街、东钱湖、宁波老外滩、樱花公园。

获取景点对应的地理坐标,可使用两种方式,一种是在高德地图API逐个查找,优点是坐标不会出错(尤其是出现重名地点或者地图软件地名模糊查询查出多个地点的时候);另一种是直接调用API获得坐标,优点是快速(尤其在有大量地点需要查询的时候)。

本文使用后者来查询地址坐标。API参数可参考地理/逆地理编码-API文档。

参考示例构建所需的API,默认返回的是JSON数据格式,可使用 jsonlite 包中的 fromJSON 函数获取。

library(tidyverse)
library(jsonlite) # fromJSON 用于获取JSON格式的数据
key <- your_key # 使用在前文提到的key
# 要游玩的景点(地点前加入宁波两个字可以提高准确性)
visit_address <- c("宁波天一阁", "宁波博物馆", "宁波南塘老街", "宁波东钱湖", "宁波老外滩", "宁波樱花公园")
# 出发地点
start_address <- c("宁波火车站")# 获取地点对应坐标函数,输入地点向量,输出坐标向量
get_location <- function(address){location_vector <- vector(length = length(address), mode = "character")for (i in seq_along(address)) {url<- str_c("https://restapi.amap.com/v3/geocode/geo?key=", key, "&address=", address[i]) location <- fromJSON(url) %>% as.data.frame() %>% select(geocodes.location)location_vector[i] <- location[1,1]}return(location_vector)
}visit_location <- get_location(visit_address) # 旅游地点坐标
start_location <- get_location(start_address) # 开始地点坐标

计算两个位置之间的距离与各种交通方式所需的时间

参考路径规划-API文档-开发指南-Web服务 API | 高德地图API可以调用步行、公交、驾车等交通方式,本文使用驾驶这种交通方式。

dt_location <- data.frame(地点 = c(start_address, visit_address), 坐标 = c(start_location, visit_location))addressA_to_B <- data.frame(出发点 = dt_location$地点, 结束点 = dt_location$地点) %>% expand.grid() %>%left_join(dt_location, by=c("出发点" = "地点")) %>%rename(出发点坐标 = 坐标) %>%left_join(dt_location, by=c("结束点" = "地点")) %>% rename(结束点坐标 = 坐标) %>%filter(出发点 != 结束点)# 构建计算行车距离与行车时长的函数
get_distance_and_duration <- function(origin, destination){driving_distance <- vector(length = length(origin), mode = "numeric")driving_duration <- vector(length = length(origin), mode = "numeric")for(i in seq_along(origin)){url<- str_c("https://restapi.amap.com/v3/direction/driving?origin=", origin[i], "&destination=", destination[i], "&key=", key)driving_distance_and_duration <- fromJSON(url) %>% as.data.frame() %>% select(route.paths.distance, route.paths.duration)driving_distance[i] <- driving_distance_and_duration$route.paths.distance[1]driving_duration[i] <- driving_distance_and_duration$route.paths.duration[1]}return(data.frame(driving_distance, driving_duration))
}distance_and_duration <- get_distance_and_duration(addressA_to_B$出发点坐标, addressA_to_B$结束点坐标)addressA_to_B_mix <- bind_cols(addressA_to_B, distance_and_duration) %>%mutate(驾驶时长min = as.numeric(driving_duration)/60, 驾驶距离km = as.numeric(driving_distance)/1000) %>%select(-driving_duration, -driving_distance)

运行后得到出发点与结束点之间的驾驶时长与驾驶距离,在文中除了计算A点到B点的驾驶距离,也计算B点到A点的驾驶距离,为了避免出现单行道等来回线路不一致的情况。

模拟各种游玩顺序,评估时长

首先构建构建旅游顺序,以宁波火车站开始,旅游玩6个景点,最后回到宁波火车站。

visit_address_copy <- data.frame(visit_address)
for (i in 1:(length(visit_address)-1)) {visit_address_copy <- bind_cols(visit_address_copy, visit_address)
}
order_of_visit <- expand.grid(visit_address_copy)
names(order_of_visit) <- paste("地点", 1:ncol(order_of_visit), sep = "")duplicate_address <- apply(order_of_visit, 1, function(x) max(table(x)))order_of_visit$出发点 <- start_address
order_of_visit$终点 <- start_address
order_of_visit$最大重复 <- duplicate_addressorder_of_visit <- order_of_visit %>% filter(最大重复 == 1) %>% select(出发点, everything(), -最大重复)

计算每种路线的驾驶时长与驾驶距离。

visit_address_copy <- data.frame(visit_address)
for (i in 1:(length(visit_address)-1)) {visit_address_copy <- bind_cols(visit_address_copy, visit_address)
}
order_of_visit <- expand.grid(visit_address_copy)
names(order_of_visit) <- paste("地点", 1:ncol(order_of_visit), sep = "")duplicate_address <- apply(order_of_visit, 1, function(x) max(table(x)))order_of_visit$出发点 <- start_address
order_of_visit$终点 <- start_address
order_of_visit$最大重复 <- duplicate_addressorder_of_visit <- order_of_visit %>% filter(最大重复 == 1) %>% select(出发点, everything(), -最大重复)all_distance_duration <- data.frame(驾驶时长min = rep(0, nrow(order_of_visit)), 驾驶距离km = rep(0, nrow(order_of_visit)))
for(i in 1:(ncol(order_of_visit)-1)){period_visit <- order_of_visit[,i:(i+1)]names(period_visit) <- c("出发点", "结束点")period_distance_duration <- period_visit %>% left_join(addressA_to_B_mix, by = c("出发点", "结束点")) %>% select(驾驶时长min, 驾驶距离km)all_distance_duration <- all_distance_duration + period_distance_duration
}order_of_visit_distance_duration <- bind_cols(order_of_visit, all_distance_duration)

 最终结果,驾驶时长最短的是如下方案,总共驾驶时长2个小时不到一点。

驾驶路程最短的是如下方案。两者的前后顺序相反, 是由一些微小的道路差异引起。

问题解决

按照什么顺序游玩在路上乘车的时间最短?

方案:直接模仿上文可解决。

如何在固定的时间时长内浏览最多的景点?

方案:在上文基础上匹配上各个浏览景点的预计浏览时长,计算总时长后在限制时长内挑选想要的旅游顺序。若最短的时长仍然高于限制时长,去掉一个你相对不喜欢的景点后再进行测算。或者直接在代码中调整,在所有length(visit_address) 后多减1。

晚上在哪住宿比较合适?(如果要住宿)

方案:将出发点设置为住宿的地点即可,比较多个住宿点,选出旅游所有目标景点最短乘车时间中最短的住宿点。

这篇关于宁波一日游(调用高德开放平台)的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/201148

相关文章

Java中将异步调用转为同步的五种实现方法

《Java中将异步调用转为同步的五种实现方法》本文介绍了将异步调用转为同步阻塞模式的五种方法:wait/notify、ReentrantLock+Condition、Future、CountDownL... 目录异步与同步的核心区别方法一:使用wait/notify + synchronized代码示例关键

Python调用Orator ORM进行数据库操作

《Python调用OratorORM进行数据库操作》OratorORM是一个功能丰富且灵活的PythonORM库,旨在简化数据库操作,它支持多种数据库并提供了简洁且直观的API,下面我们就... 目录Orator ORM 主要特点安装使用示例总结Orator ORM 是一个功能丰富且灵活的 python O

Java调用DeepSeek API的最佳实践及详细代码示例

《Java调用DeepSeekAPI的最佳实践及详细代码示例》:本文主要介绍如何使用Java调用DeepSeekAPI,包括获取API密钥、添加HTTP客户端依赖、创建HTTP请求、处理响应、... 目录1. 获取API密钥2. 添加HTTP客户端依赖3. 创建HTTP请求4. 处理响应5. 错误处理6.

Deepseek R1模型本地化部署+API接口调用详细教程(释放AI生产力)

《DeepseekR1模型本地化部署+API接口调用详细教程(释放AI生产力)》本文介绍了本地部署DeepSeekR1模型和通过API调用将其集成到VSCode中的过程,作者详细步骤展示了如何下载和... 目录前言一、deepseek R1模型与chatGPT o1系列模型对比二、本地部署步骤1.安装oll

一分钟带你上手Python调用DeepSeek的API

《一分钟带你上手Python调用DeepSeek的API》最近DeepSeek非常火,作为一枚对前言技术非常关注的程序员来说,自然都想对接DeepSeek的API来体验一把,下面小编就来为大家介绍一下... 目录前言免费体验API-Key申请首次调用API基本概念最小单元推理模型智能体自定义界面总结前言最

JAVA调用Deepseek的api完成基本对话简单代码示例

《JAVA调用Deepseek的api完成基本对话简单代码示例》:本文主要介绍JAVA调用Deepseek的api完成基本对话的相关资料,文中详细讲解了如何获取DeepSeekAPI密钥、添加H... 获取API密钥首先,从DeepSeek平台获取API密钥,用于身份验证。添加HTTP客户端依赖使用Jav

redis防止短信恶意调用的实现

《redis防止短信恶意调用的实现》本文主要介绍了在场景登录或注册接口中使用短信验证码时遇到的恶意调用问题,并通过使用Redis分布式锁来解决,具有一定的参考价值,感兴趣的可以了解一下... 目录1.场景2.排查3.解决方案3.1 Redis锁实现3.2 方法调用1.场景登录或注册接口中,使用短信验证码场

使用C/C++调用libcurl调试消息的方式

《使用C/C++调用libcurl调试消息的方式》在使用C/C++调用libcurl进行HTTP请求时,有时我们需要查看请求的/应答消息的内容(包括请求头和请求体)以方便调试,libcurl提供了多种... 目录1. libcurl 调试工具简介2. 输出请求消息使用 CURLOPT_VERBOSE使用 C

Python调用另一个py文件并传递参数常见的方法及其应用场景

《Python调用另一个py文件并传递参数常见的方法及其应用场景》:本文主要介绍在Python中调用另一个py文件并传递参数的几种常见方法,包括使用import语句、exec函数、subproce... 目录前言1. 使用import语句1.1 基本用法1.2 导入特定函数1.3 处理文件路径2. 使用ex

Idea调用WebService的关键步骤和注意事项

《Idea调用WebService的关键步骤和注意事项》:本文主要介绍如何在Idea中调用WebService,包括理解WebService的基本概念、获取WSDL文件、阅读和理解WSDL文件、选... 目录前言一、理解WebService的基本概念二、获取WSDL文件三、阅读和理解WSDL文件四、选择对接