前言在当今数字化时代地理信息系统GIS技术已经深入到我们生活的方方面面。无论是日常出行规划、物流配送优化还是城市交通管理路线规划服务都扮演着至关重要的角色。而百度地图作为国内地图服务提供商其强大的路线规划 API 为开发者提供了丰富的功能和数据支持。基于 Java 开发语言结合百度地图的路线规划服务不仅可以实现高效、精准的路线规划还能通过 Java 的强大生态和企业级应用能力为各类应用场景提供稳定可靠的解决方案。本文将以 Java 编程语言为例详细的对百度地图开放平台的驾车路线规划服务进行介绍不仅详细的介绍其 API 和请求响应参数同时还以 Java 为例讲解如何对平台返回的对象进行对应的封装通过自定义封装的结果。可以为后续的数据持久化和数据挖掘分析提供坚实的数据基础。文章首先详细的介绍百度地图的驾车路线服务包括接口请求参数和响应参数。然后详细介绍在 Java 当中如何集成路径规划服务并且将官方的 JSON 转换成我们的 JavaBean。通过本文您不仅可以掌握百度驾车路线规划的相关内容同时可以了解如何自己来封装和定义相关业务对象无论您是地理应用开发爱好者还是 GIS 开发工程师均可以学习实践。驾车路线服务简介本节将对百度地图的驾车路线服务进行简单的介绍。这不仅是我们开发的重要文档也是我们后续进行问题查找的重要资料。这里将详细的介绍百度地图提供哪些规划服务、驾车路线服务包括哪些以及驾车路线服务的请求参数和响应参数信息。1. 百度路线规划服务路线规划服务又名 Direction API 是一套 REST 风格的 Web 服务 API以 HTTP/HTTPS 形式提供了路线规划服务。从上图可以看到百度地图的路线规划服务视图是非常丰富的不仅包含驾车的方式还包含骑行、步行和公交。大家可以根据自己的业务需要来调用相应的服务即可。更多服务能力大家可以访问百度开放平台的相关链接了解。2. 驾车路线服务驾车服务作为路线服务中非常重要的一环。如今随着城市交通建设的大力发展许多城市的道路建设几乎是日新月异如果没有路线导航服务出行一定会受到极大的限制。百度驾车路线服务根据起终点坐标检索符合条件的驾车路线规划方案支持以下功能支持一次请求返回多条路线备用路线支持18个以内的途径点支持传入车牌规避限行路段支持传入起点车头方向辅助判断起点所在正逆向车道辅助更准确算路支持未来出行规划指定未来7天任意出发时刻将依据智能预测路况和道路限行规划合理路线驾车路线服务的访问地址如下https://api.map.baidu.com/direction/v2/driving?origin40.01116,116.339303destination39.936404,116.452562ak您的AKUniHttp接口访问集成这里我们使用 UniHttp 来简化 Http 服务调用关于如何快速集成 UniHttp 可以查询官网也可以私信留言。1. 访问接口创建import com.burukeyou.uniapi.http.annotation.param.QueryPar; import com.burukeyou.uniapi.http.annotation.request.GetHttpInterface; import com.burukeyou.uniapi.http.core.response.HttpResponse; /** * - 百度驾车路径规划服务2.0版本 * */ public interface BaiduDrivingV2Service { GetHttpInterface(path /direction/v2/driving) /** * - 驾车路线规划 * param ak 用户的访问权限AK申请 * param origin - 起点经纬度小数点后不超过6位40.056878,116.30815 * param destination -终点经纬度小数点后不超过6位40.056878,116.30815 * param coordType - 坐标类型可选参数默认为bd09ll。允许的值为bd09ll百度经纬度坐标、bd09mc百度墨卡托坐标、gcj02国测局加密坐标、wgs84gps设备获取的坐标。 * param retCoordtype 返回结果坐标类型默认为bd09ll允许的值为bd09ll百度经纬度坐标、gcj02国测局加密坐标 * param tactics 0默认、2距离最短只返回一条路线不考虑限行和路况距离最短且稳定用于估价场景 * 3不走高速、4高速优先、5躲避拥堵、6少收费、7: 躲避拥堵 高速优先 * 8: 躲避拥堵 不走高速、9: 躲避拥堵 少收费、10: 躲避拥堵 不走高速 少收费 * 11: 不走高速 少收费、12: 距离优先考虑限行和路况距离相对短且不一定稳定、13时间优先 * param alternatives 是否返回备选路线类型string。选值0返回一条推荐路线 1返回1-3条路线供选择 * param cartype 车辆类型区分车辆是普通燃油车或纯电动汽车。由于部分城市对燃油车和电动车限行规则有差异该字段用于结合plate_number车牌号来规避限行。例如纯电动汽车在北京本地无尾号限行而燃油车需遵守尾号限行。可选值0普通汽车、1纯电动汽车 * param speed 起点车辆的行驶速度字段类型float * param stepsInfo 是否下发step详情。1下发step详情 0不下发step详情 * return */ public HttpResponseString getSearch(QueryPar(ak) String ak, QueryPar(origin) String origin, QueryPar(destination) String destination, QueryPar(coord_type) String coordType, QueryPar(ret_coordtype) String retCoordtype, QueryPar(tactics) int tactics, QueryPar(alternatives) int alternatives, QueryPar(cartype) int cartype, QueryPar(speed) float speed, QueryPar(steps_info) int stepsInfo ); }以上参数是根据业务的需求进行定义的除必填的参数以外很多选填的参数是可以不定义直接使用默认值即可。2. 本地调用测试下面我们以从广东省广州市为起点驾车开往贵州省铜仁市为例车速选择匀速100公里车型为普通油车、需要返回备选路线、并且返回下发详情的实例进行接口请求。这里我们使用Junit的方式进行集成核心代码如下import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.boot.test.context.SpringBootTest; import org.springframework.test.context.junit4.SpringRunner; import com.burukeyou.uniapi.http.core.response.HttpResponse; /** * - 百度地图驾车服务测试类 * */ SpringBootTest RunWith(SpringRunner.class) public class BaiduDrivingV2ServiceCase { private static final String BAIDU_CLIENT_AK yourak; Autowired private BaiduDrivingV2Service drivingService; Test public void testDriving() { String origin 23.115102,113.269043;//出发地广东省广州市 String destination 27.728514,109.186249;//目的地贵州省铜仁市 String coordType wgs84; String retCoordtype bd09ll;//返回坐标类型请跟入参的坐标类型有所区别返回坐标不支持WGS84 int tactics 0;//默认距离最短 int alternatives 1;//1表示返回1-3条备选路线 int cartype 0;//普通油车 float speed 27.78F;//100千米/小时 ≈ 27.78米/秒 int stepsInfo 1;//下发详情 HttpResponseString result drivingService.getSearch(BAIDU_CLIENT_AK, origin, destination, coordType, retCoordtype, tactics, alternatives, cartype, speed, stepsInfo); System.out.println(result.getBodyResult()); } }3. 响应对象初探在本地IDE中运行以上程序后可以看到以下输出在文本编辑器中对返回数据进行json格式化后可以看到如下结构这个结构很重要这个结构是我们下一步进行Java对象封装的重要参考资料。响应对象的 Java 封装通过上一节我们已经成功的获取到了百度地图开放平台返回的路径规划结果数据格式是json在实际业务中我们需要使用Java来进行数据的持久化或者数据挖掘因此需要将json反序列化成JavaBean。这里分别介绍响应类图、以及相应的实现最后基于GSON来进行对象转换说明。1. 驾车路线服务响应类图根据前面的响应参数介绍以及在上一小节的真实响应对象的研究我们大致对返回对象有了一个初印象。整理成如下类图根据业务的需要为了完整的业务数据还原这里设计11个类来对百度地图的路线规划服务接口返回数据进行接收。2. 响应对象实现公共属性类公共对象是所有百度公共接口的父类用来定义响应数据的公共属性定义如下import java.io.Serializable; import lombok.AllArgsConstructor; import lombok.Getter; import lombok.NoArgsConstructor; import lombok.Setter; import lombok.ToString; /** * - 百度接口公共DTO对象用于封装通用信息 */ NoArgsConstructor AllArgsConstructor Setter Getter ToString public class BdCommonDTO implements Serializable { private static final long serialVersionUID 4985268844473756688L; private int status;//状态码 本次API访问状态如果成功返回0如果失败返回其他数字。 private String message;//响应信息 对status的中文描述 }驾车路线数据传输类驾车路线数据传输类封装了规划的路线信息核心代码如下import java.io.Serializable; import lombok.AllArgsConstructor; import lombok.EqualsAndHashCode; import lombok.Getter; import lombok.NoArgsConstructor; import lombok.Setter; import lombok.ToString; NoArgsConstructor AllArgsConstructor Setter Getter ToString(callSupertrue)//callSupertrue表示输出父类属性 EqualsAndHashCode(callSupertrue) public class BdDrivingDTO extends BdCommonDTO implements Serializable{ private static final long serialVersionUID 5055488530865458258L; private Integer type;//默认返回2开发者无需关注 private BdDrivingResultDTO result; }导航信息类导航信息类包含了分段信息、方案总数、具体的方案路线信息核心代码如下import java.io.Serializable; import java.util.List; import com.google.gson.annotations.SerializedName; import lombok.AllArgsConstructor; import lombok.Getter; import lombok.NoArgsConstructor; import lombok.Setter; import lombok.ToString; NoArgsConstructor AllArgsConstructor Setter Getter ToString public class BdDrivingResultDTO implements Serializable{ private static final long serialVersionUID 6407644142297216118L; private String restriction;//限行结果提示信息若无限行路线则返回空若无法规避限行则返回限行提示信息 private int total;//返回方案的总数 SerializedName(navi_restype) private String naviRestype; SerializedName(session_id) private String sessionId; private ListBdDrivingRouteDTO routes; private String holiday; SerializedName(ret_coordtype) private String retCoordtype; SerializedName(api_restype) private String apiRestype; }具体路线分段信息类具体路线分段信息类封装了路线详情、距离、打车费用预估、预计时间和具体的转折路线列表核心代码如下import java.io.Serializable; import java.util.List; import com.google.gson.annotations.SerializedName; import lombok.AllArgsConstructor; import lombok.Getter; import lombok.NoArgsConstructor; import lombok.Setter; import lombok.ToString; NoArgsConstructor AllArgsConstructor Setter Getter ToString public class BdDrivingRouteDTO implements Serializable{ private static final long serialVersionUID -2475019111446934340L; private BdLocationDTO origin; private BdLocationDTO destination; private String tag;//方案标签 private String mrsl; SerializedName(route_md5) private String routeMd5; SerializedName(data_version) private String dataVersion; SerializedName(traffic_light) private int trafficLight; private float distance;//距离单位米 private int duration;//未来驾车路线耗时单位秒 SerializedName(taxi_fee) private float taxiFee; SerializedName(has_guidance) private boolean hasGuidance; private ListBdDrivingStepDTO steps;//路线分段集合 SerializedName(restriction_info) private BdDrivingRestrictionInfoDTO restrictionInfo; SerializedName(yellow_tip) private ListBdDrivingYelloTipDTO yellowTipList; private int toll;//此路线道路收费单位元 SerializedName(toll_distance) private float tollDistance; private float score; SerializedName(route_id) private String routeId; }篇幅有限如果百度驾车路径规划完整响应类的代码可以参考上述的结果先自己研究如有问题可以私信博主就具体的类进行交流。常见问题在百度驾车路线规划服务集成过程中可能会遇到一些问题。比如我在集成过程中就遇到了关于坐标精度和坐标和格式的问题。导致这个问题的原因主要还是对官网文档不是很熟悉实践出真知纸上得来终觉浅只有经过实战才知道可能会遇到什么问题。1. 坐标顺序问题众所周知在地理位置中经纬度是描述一个点的具体格式。因此我们特别习惯在描述一个点时使用经度,纬度的方式如113.269043,23.115102。但是这种方式在实际查询过程中会报以下错误解决的办法也比较简单在百度的位置描述中将纬度描述在前即纬度经度即可。2. 坐标格式问题坐标类型永远是GIS应用中绕不开的话题大家可能都以为通用的WGS84在接口的参数定义中我们可以看到查询参数的坐标是支持WGS84的但是在返回的坐标中却没有了这个参数支持。如果在返回参数中设置了WGS84大概率是会报错的如下图所示解决办法就是按照文档调整参数设置即可。 福利时间如果你正在备战面试或者想要学习其他知识给大家推荐一个宝藏知识库作者整理了一些列 Java 程序员需要掌握的核心知识有需要的自取不谢。知识库地址https://farerboy.com/