浅谈利用SQLite存储离散瓦片的思路和实现方法

摘要:
使用SQLite一般只需要带上它的一个动态库,就可以享受它的全部功能。SQLite的API不区分当前操作的数据库是在内存还是在文件。使用MBTiles进行存储,也能实现便于部署的目的。

文章版权由作者李晓晖和博客园共有,若转载请于明显处标明出处:http://www.cnblogs.com/naaoveGIS/

1.背景

在多个项目中涉及到互联网地图的内网显示,通过自制工具完成了互联网地图的瓦片下载。但是此种方法存在如下几个问题:

a.瓦片均是离散型图片,远程部署非常耗时。

b.瓦片下载中,涉及到将互联网瓦片下载至内存,然后建立对应文件夹,然后保存至本地的过程,效率不高。

除了以上两个问题外,还有存储占用比较多等等缺点。是否有类似于ArcGIS的Bundle型瓦片组织格式来解决存储占用、远程部署等已有问题的解决方案?

浅谈利用SQLite存储离散瓦片的思路和实现方法第1张

2.自定义Bundle格式

2.1利用Sqlite进行存储

2.1.1Sqlite的优点

a. 轻量级

SQLite和C/S模式的数据库软件不同,它是进程内的数据库引擎,因此不存在数据库的客户端和服务器。使用SQLite一般只需要带上它的一个动态库,就可以享受它的全部功能。

这样非常便于我们将其作为一个文件来看待。

b. 单一文件

所谓的“单一文件”,就是数据库中所有的信息(比如表、视图、触发器、等)都包含在一个文件内。并且这个文件可以copy到其它目录或其它机器上,也同样可以使用。

通过这个单一文件性,我们便可以将本身需要离散存储的文件进行统一管理了。

c. 跨平台/可移植性

除了主流操作系统,SQLite还支持了很多冷门的操作系统,比如Android、Windows Mobile、Symbin、Palm、VxWorks等的支持。

一次存储,多点使用。

d.内存数据库(in-memory database
目前内存越来越廉价, SQLite的内存数据库特性就越发显得好用。SQLite 的API不区分当前操作的数据库是在内存还是在文件(对于存储介质是透明的)。所以如果你觉得磁盘I/O有可能成为瓶颈的话,可以考虑切换 为内存方式。切换的时候,操作SQLite的代码基本不用大改,只要在开始时把文件Load到内存,结束时把内存的数据库Dump回文件就可以了。

在存储瓦片时,如果瓦片数据不算多,内存足够用,可以切换为内存方式,进一步提高瓦片读取效率。

2.1.2缺点

a.并发访问的锁机制

SQLite在并发(包括多进程和多线程)读写方面的性能一直不太理想。数据库可能会被写操作独占,从而导致其它读写操作阻塞或出错。

b. SQL标准支持不全
在它的官方网站上,具体列举了不支持哪些SQL92标准。

2.2 瓦片以MBTiles规范进行组织

MBTiles 是一种地图瓦片存储的数据规范,可大大提高海量地图瓦片的读取速度,比通过瓦片文件方式的读取要快很多,适用于Android、IPhone等智能手机的离线地图存储。

MBTiles通过视图,可以重复使用冗余瓦片数据,从而减少瓦片占用的空间,而不是一个单一的、文字表。比如:地图覆盖大面积的纯蓝色像海洋或空的土地,造成成千上万的重复、冗余的瓦片数据,例如,4/2/8的瓦片在太平洋中间,可能看起来就是一张蓝色图片虽然它可能是一些处于第3级,但在16级可能存在数以百万计的蓝色图片,他们都完全一样。

MBTiles通用方法是将瓦片表分成两张:一个用来存储原始图像和一个存储瓷砖坐标对应那些图片。具体设计如下:

a.设计map

浅谈利用SQLite存储离散瓦片的思路和实现方法第2张

对瓦片行列号以及对应的瓦片ID进行存储。

b.设计images

浅谈利用SQLite存储离散瓦片的思路和实现方法第3张

对瓦片进行存储。

c.设计视图tiles

浅谈利用SQLite存储离散瓦片的思路和实现方法第4张

基于map和images生成。

3.开发瓦片下载和打包存储工具

3.1瓦片下载工具

瓦片下载工具基于瓦片寻址算法开发,针对不同互联网地图,瓦片的行列号算法等稍有不同。尤其是针对百度地图,其瓦片算法会按照百度的瓦片分级偏移规则进行换算。这里不做累述。

浅谈利用SQLite存储离散瓦片的思路和实现方法第5张

3.2基于MBTiles规范进行存储

设计思路为:

a.多线程瓦片下载,内存中开辟容器池。

b.当内存容器池满后,进行整体入库至sqlite。入库时进行上锁,规避Sqlite对多事务支持不理想问题。

浅谈利用SQLite存储离散瓦片的思路和实现方法第6张

4.改造后端进行测试

4.1改造后端

后端按照连接池的思想,支持通过行列号在Sqlite中读取到瓦片。

4.2前端测试

浅谈利用SQLite存储离散瓦片的思路和实现方法第7张

5.方案优点总结

a.提高瓦片下载存储速度。经测试,比本地图片存储方式效率至少提高一倍。主要由于,一是二进制存储,无转换过程。二是减少各层级文件夹建立耗时。

b.减少存储空间。MBTiles规范可以减少冗余瓦片。

c.便于数据转移。所有瓦片存储于一个文件夹中,便于数据转移部署。

d.提高海量地图瓦片的读取速度,比通过瓦片文件方式的读取要快很多。原因为单个文件不再涉及到目录寻址,并且也不需要将瓦片读取为二进制再传出。

6.待测试

由于sqlite本身对多事务支持不是很良好,大并发访问瓦片的情景还需测试。下一步准备使用Jmeter进行测试。

7.扩展使用

目前矢量切图工具,存储的也均是离散型的PBF。使用MBTiles进行存储,也能实现便于部署的目的。并且,一个图层使用一个视图,这种概念与ArcGIS中的图层入库也更为相似。

-----欢迎转载,但保留版权,请于明显处标明出处:http://www.cnblogs.com/naaoveGIS/

如果您觉得本文确实帮助了您,可以微信扫一扫,进行小额的打赏和鼓励,谢谢 ^_^

浅谈利用SQLite存储离散瓦片的思路和实现方法第8张

免责声明:文章转载自《浅谈利用SQLite存储离散瓦片的思路和实现方法》仅用于学习参考。如对内容有疑问,请及时联系本站处理。

上篇关于微信小程序map地图的使用ThinkPhp5 mongodb 使用自定义objectID出错解决下篇

宿迁高防,2C2G15M,22元/月;香港BGP,2C5G5M,25元/月 雨云优惠码:MjYwNzM=

相关文章

B14-iOS开发中的几种存储方式

一、NSUserDefault(偏好设置,Preference) 小规模数据,弱业务相关数据使用。例:某个UISwitch的状态。 二、File(文件存储) 文件存储包括了Plist、archive、Stream等方式,一般结构化的数据或者需要方便查询的数据,都会以Plist的方式去持久化。 Archive方式适合存储平时不太经常使用但很大量的数据,或者读...

python系列之(3)爬取豆瓣图书数据

上次介绍了beautifulsoup的使用,那就来进行运用下吧。本篇将主要介绍通过爬取豆瓣图书的信息,存储到sqlite数据库进行分析。 1.sqlite SQLite是一个进程内的库,实现了自给自足的、无服务器的、零配置的、事务性的 SQL 数据库引擎。它是一个零配置的数据库,这意味着与其他数据库一样,您不需要在系统中配置。 就像其他数据库,SQLite...

SQLite学习之自增列(03)

ID列一定要为自增 然后,系统会自动增加一个sqlite_sequence表,sqlite_sequence表也是SQLite的系统表。该表用来保存其他表的RowID的最大值。数据库被创建时,sqlite_sequence表会被自动创建。该表包括两列。第一列为name,用来存储表的名称。第二列为seq,用来保存表对应的RowID的最大值。该值最大值为922...

基础方法或属性: 列表,元组,字典,字符串,集合及内置函数等(注:只有英文名)

列表 list append clear copy count extend index insert pop remove reverse sort 元组 tuple count index 字典 dict clear copy fromkeys get items keys pop popitem setdefault update values 字...

各种数据库与.NET Framework类型对照

本文记录各种数据库与.NET类型的对照,包括Oracle,SQL Server,MySQL,SQLite 首先是Oracle的 序号 Oracle数据类型 .NET类型 1 BFILE byte[] 2 BLOB byte[] 3 CHAR string 4 CLOB string 5 DATE DateTime 6 FLO...

Ubuntu下用脚本执行sql语句(sqlite)

1、环境准备,安装sqlite3软件 sudo apt-get install sqlite3 2、编写sql执行脚本(更新操作),每条sql语句以分号结束,sql.sql文件内容: ALTER TABLE "GameDeviceInfo" ADD "Delay" INTEGER NOT NULL DEFAULT 0; ALTER TABLE "GameD...