目录
- 背景
- 粗暴简单字符串
- 示例
- 数组套数组
- 示例
- LineString+WKT来帮忙
- 参考资料
背景
现有一条路,这条路由好几段路段构成,每个路段又由一些轨迹点先后连接而成,且这些轨迹点数量不固定,有些路段由10个轨迹点连接而成,有些路段由30个轨迹点连接而成,而有些只由2个轨迹点连接而成,每个轨迹点又由一对经纬度组成,想办法把这些轨迹点存入clickhouse里,一般有以下三种方法。
-
方法一 粗暴简单字符串
-
方法二 数组套数组
-
方法三 LineString+WKT来帮忙
粗暴简单字符串
也许你会抱怨,又给我整字符串,感觉字符串就是万精油,这不,在处理经纬度路径数据也能用得上,可以这么去想,让某路段的所有轨迹点都做成一个字符串,笼统的塞进某个字段里面去便是,只是后期取数的时候略微麻烦,需要tolist改过来。
示例
- 建表
CREATE TABLE ods_car.ads_roadTrajectory1_local on cluster cluster_1shards_3replicas
(
`id` Int32 COMMENT '路段号',
`segment_trajectory` String COMMENT '路段中的轨迹点'
)
ENGINE = ReplicatedReplacingMergeTree('/clickhouse/tables/{shard}/ads_roadTrajectory1_local',
'{replica}')
ORDER BY id
SETTINGS storage_policy = 'three_tier',
index_granularity = 8192;
CREATE TABLE ods_car.ads_roadTrajectory1 on cluster cluster_1shards_3replicas
(
`id` Int32 COMMENT '路段号',
`segment_trajectory` String COMMENT '路段中的轨迹点'
)
ENGINE = Distributed('cluster_1shards_3replicas',
'ods_car',
'ads_roadTrajectory1_local',
rand());
- 查表
select id, segment_trajectory
from ods_car_network.ads_roadTrajectory1;
此时应该是一个由2个字段构成的空表。
- 插入数据
INSERT INTO ods_car_network.ads_roadTrajectory1(id,segment_trajectory)
VALUES(
1,
'[[109.97939898149895, 39.310716681169026],[109.9793989813902, 39.310715680670924]]'
);
- 验证
select id, segment_trajectory, toTypeName(segment_trajectory)
from ods_car_network.ads_roadTrajectory1;
可以看到segment_trajectory字段的类型是String。
数组套数组
如果点的经纬度在前期就被写成数组结构,一个点一对经纬度对,一个2个元素组成的数组,都是如下这样的
[ 116.397128 , 39.916527 ] [116.397128, 39.916527] [116.397128,39.916527]
那么,可以使用ClickHouse的Array类型来存储。path列是Array类型,用于存储经纬度点的数组。
示例
- 建表
CREATE TABLE ods_car.ads_roadTrajectory1_local on cluster cluster_1shards_3replicas
(
`id` Int32 COMMENT '路段号',
`segment_trajectory` Array(Array(Float32)) COMMENT '路段中的轨迹点'
)
ENGINE = ReplicatedReplacingMergeTree('/clickhouse/tables/{shard}/ads_roadTrajectory1_local',
'{replica}')
ORDER BY id
SETTINGS storage_policy = 'three_tier',
index_granularity = 8192;
CREATE TABLE ods_car.ads_roadTrajectory1 on cluster cluster_1shards_3replicas
(
`id` Int32 COMMENT '路段号',
`segment_trajectory` Array(Array(Float32)) COMMENT '路段中的轨迹点'
)
ENGINE = Distributed('cluster_1shards_3replicas',
'ods_car',
'ads_roadTrajectory1_local',
rand());
- 查表
select id, segment_trajectory
from ods_car_network.ads_roadTrajectory1;
- 插入数据
INSERT INTO ods_car.ads_roadTrajectory1(id,segment_trajectory)
VALUES(
1,
[[109.97939898149895, 39.310716681169026],[109.9793989813902, 39.310715680670924]]
);
此时,可以再次查表看一下效果
segment_trajectory列是Array类型,用于存储经纬度点的数组。该路径由2个点组成,分别是(109.97939898149895, 39.310716681169026)、(109.9793989813902, 39.310715680670924)。
如果要查询path表中所有路径的ID、名称和经纬度点,可以使用以下示例查询语句
SELECT id, segment_trajectory FROM ods_car.ads_roadTrajectory1;
这个语句将查询ads_roadTrajectory1表中所有路径的ID、和构成这个路径的经纬度点对,在结果中,经纬度点以数组形式返回,方便其他脚本语音如python索引提取。
LineString+WKT来帮忙
在ClickHouse中,可以使用GeoSpatial数据类型来存储经纬度点的路径。GeoSpatial数据类型支持存储点、线和多边形等地理空间数据,需要提前安装安装Geospatial扩展,该扩展提供了许多地理空间数据类型和函数,包括LineString类型。
CREATE DATABASE IF NOT EXISTS geospatial;
USE geospatial;
CREATE TABLE dummy (dummy UInt8) ENGINE = Memory;
INSERT INTO dummy VALUES (1);
INSTALL EXTENSION geospatial;
安装好拓展后,对于一段有经纬度点的路径,可以使用LineString类型来存储。LineString是由多个点组成的线段,可以表示路径或路线。每个点由经度和纬度两个值组成。
以下是一个示例表结构,用于存储经纬度点的路径:
CREATE TABLE path (
id UInt64,
name String,
path LineString
) ENGINE = MergeTree()
ORDER BY id;
在这个表中,id和name是普通的列,用于存储路径的ID和名称。path列是LineString类型,用于存储路径的经纬度点。
可以使用WKT(Well-Known Text)格式来插入和查询LineString类型的数据。以下是一个示例插入语句:
INSERT INTO path VALUES (1, 'path1', 'LINESTRING(116.397128 39.916527, 116.397524 39.917081, 116.398129 39.917441)');
这个语句将一条名为path1的路径插入到path表中。该路径由三个点组成,分别是(116.397128, 39.916527)、(116.397524, 39.917081)和(116.398129, 39.917441)。
可以使用ST_AsText函数将LineString类型的数据转换为WKT格式。以下是一个示例查询语句:
SELECT id, name, ST_AsText(path) FROM path;
这个语句将查询path表中所有路径的ID、名称和经纬度点,并将经纬度点转换为WKT格式。
注,使用Geospatial扩展需要在ClickHouse服务器上安装GEOS库,如果您没有安装GEOS库,请先安装它,并且确保有相应的权限,否则会报错
Code: 50, e.displayText() = DB::Exception: Unknown data type family: LineString.
参考资料
1,https://blog.csdn.net/u010882234/article/details/130588280
2,https://blog.csdn.net/PengPengBlog/article/details/80142485