还在用Shapefile?GeoJSON才是WebGIS的未来!你了解多少?

在空间矢量数据处理这一领域,GeoJSON格式越来越受到关注。然而,对于许多人来说,在Java中使用GDAL来处理它却显得有些困难。这其中牵涉到多种工具和数据库操作,内容虽然复杂,但实则极具价值。

QGIS展示GeoJSON数据

{
    "type": "FeatureCollection",
    "features": [{
            "type": "Feature",
            "geometry": {
                "type": "Point",
                "coordinates": [102.0, 0.5]
            },
            "properties": {
                "prop0": "value0"
            }
        }, {
            "type": "Feature",
            "geometry": {
                "type": "LineString",
                "coordinates": [[102.0, 0.0], [103.0, 1.0], [104.0, 0.0], [105.0, 1.0]]
            },
            "properties": {
                "prop0": "value0",
                "prop1": 0.0
            }
        }, {
            "type": "Feature",
            "geometry": {
                "type": "Polygon",
                "coordinates": [[100.0, 0.0], [101.0, 0.0], [101.0, 1.0], [100.0, 1.0], [100.0, 0.0]]
            },
            "properties": {
                "prop0": "value0",
                "prop1": {
                    "this": "that"
                }
            }
        }
    ]
}

处理GeoJSON数据,我们首先可以用QGIS工具来展示。比如,我们得到了一份某地区地理信息的数据集,在适当的时候,用QGIS可以轻松展示这些数据。这样,我们就能直接观察到数据的具体内容。而且,操作起来很简便,只需按照软件的指示将GeoJSON数据加载进去,就能清楚地看到其空间属性的详细信息。这一过程为后续处理打下了基础,比如帮助我们了解数据的大致内容,检查是否有错误等。此外,QGIS在处理GeoJSON数据时,会依照既定的规则,比如识别格式中的特定标识符等。

从方便性角度考虑,QGIS工具展示数据,能让众多技术人员迅速掌握GeoJSON数据情况,便于后续复杂操作的开展。

PostGIS创建空间表

基于Java和GDAL实现的GeoJSON数据读取与入库实践

处理GeoJSON数据时,数据库需建立空间型表格。以PostGIS为例,在特定位置,建立此类表格有既定步骤。我们设计数据库表以存储GeoJSON数据,这需遵循数据库规范化原则,并满足业务需求。例如,在geom列上创建GIST索引,便于后续的空间数据查询。数据库管理员需掌握空间数据管理知识,并熟悉PostGIS操作。操作过程中,每一步都应谨慎,否则不合理的表结构设计可能影响数据入库。

基于Java和GDAL实现的GeoJSON数据读取与入库实践

从整体来看,空间表的构建质量对GeoJSON数据处理的整个过程至关重要。一旦空间表设计存在缺陷,那么后续的数据保存和检索工作很可能会遭受严重影响。

基于Java和GDAL实现的GeoJSON数据读取与入库实践

GDAL解析GeoJSON数据

基于Java和GDAL实现的GeoJSON数据读取与入库实践

GDAL在数据处理中扮演关键角色。它根据不同的数据格式,运用相应的驱动包进行解析。特别是面对GeoJSON数据,存在专门的驱动程序负责读写操作。这一过程涉及诸多技术细节,例如编写具体代码。我们根据GeoJSON在GDAL中的特性进行解析。JSON是一种轻量级文本格式,而GeoJSON则是其地理信息的专有版本。在解析时,这些特性需在代码中具体体现。

基于Java和GDAL实现的GeoJSON数据读取与入库实践

现实中,对技术人员编写代码的能力有较高要求。他们需准确理解GeoJSON数据格式在GDAL中的具体规则。一旦代码编写出错,便无法正确解析数据。

Java实体模型基础

基于Java和GDAL实现的GeoJSON数据读取与入库实践

在此环节,构建基础的Java实体模型至关重要。这构成了Java语言环境中后续操作的基础框架。除了这个基础模型,还有如Mapper和Service等对象,这些内容暂不展开代码阐述。然而,实体模型中包含了关键的数据结构及相应操作的定义,例如与空间数据相关的类与函数等。技术人员在操作时需明确其整体逻辑中的角色。

CREATE TABLE "public"."biz_geographic_name" (
  "pk_id" int8 NOT NULL,
  "name" varchar(255) COLLATE "pg_catalog"."default" NOT NULL,
  "pinyin" varchar(255) COLLATE "pg_catalog"."default",
  "classz" varchar(4) COLLATE "pg_catalog"."default",
  "bz" varchar(100) COLLATE "pg_catalog"."default",
  "slx" varchar(20) COLLATE "pg_catalog"."default",
  "geom" "public"."geometry" NOT NULL,
  CONSTRAINT "pk_biz_geographic_name" PRIMARY KEY ("pk_id")
)
;
ALTER TABLE "public"."biz_geographic_name" 
  OWNER TO "ghy01";
CREATE INDEX "idex_biz_geographic_name_classz" ON "public"."biz_geographic_name" USING btree (
  "classz" COLLATE "pg_catalog"."default" "pg_catalog"."text_ops" ASC NULLS LAST
);
CREATE INDEX "idx_biz_geographic_name_geom" ON "public"."biz_geographic_name" USING gist (
  "geom" "public"."gist_geometry_ops_2d"
);
COMMENT ON COLUMN "public"."biz_geographic_name"."pk_id" IS '主键id';
COMMENT ON COLUMN "public"."biz_geographic_name"."name" IS '地名';
COMMENT ON COLUMN "public"."biz_geographic_name"."pinyin" IS '汉语拼音';
COMMENT ON COLUMN "public"."biz_geographic_name"."classz" IS 'classz';
COMMENT ON COLUMN "public"."biz_geographic_name"."bz" IS '备注';
COMMENT ON COLUMN "public"."biz_geographic_name"."slx" IS 'slx';
COMMENT ON COLUMN "public"."biz_geographic_name"."geom" IS '空间对象';
COMMENT ON TABLE "public"."biz_geographic_name" IS '地名基础信息表,用于存储中国范围内的地名信息';

在实际应用中,Java实体模型的构建是否得当,直接影响着后续数据逻辑的准确性。这一环节是整个数据处理流程中的基础且关键部分。

将GeoJSON数据入库

利用Java语言结合GDAL工具,将GeoJSON格式的空间数据导入数据库。这是流程中的关键环节。操作时,可以直观地观察到数据库的变动,比如通过执行查询语句来确认是否已批量导入地名信息。借助navicat工具,我们可以连接数据库并查看导入结果,比如确认地级市的地名数据是否已成功添加到空间数据中。技术人员需确保数据准确无误地入库,并建立合理的关联。

这一环节标志着数据从读取、处理直至存储的全过程告一段落。若此环节出现故障,之前的努力可能全部白费。

@Test
public void readDjsGeoJSON() {
	// 指定文件的名字和路径
	String strVectorFile = "path/2015省市区县乡镇地名数据/地名点_地级市.geojson";
	// 注册所有的驱动
	ogr.RegisterAll();
	gdal.SetConfigOption("GDAL_FILENAME_IS_UTF8", "YES");
	gdal.SetConfigOption("SHAPE_ENCODING", "UTF-8");
	String strDriverName = "GeoJSON";
	org.gdal.ogr.Driver oDriver = ogr.GetDriverByName(strDriverName);
	if (oDriver == null) {
		System.out.println(strDriverName + " 驱动不可用!n");
		return;
	}
	DataSource dataSource = oDriver.Open(strVectorFile);
	Layer layer = dataSource.GetLayer(0);
	SpatialReference spatialReference = layer.GetSpatialRef();
	String srid = spatialReference.GetAttrValue("AUTHORITY", 1);
	long featureCount = layer.GetFeatureCount();
	List list = new ArrayList();
	for (int i = 0; i < featureCount; i++) {
		Feature feature = layer.GetFeature(i);
		String name = feature.GetFieldAsString("NAME");
		String pinyin = feature.GetFieldAsString("PINYIN");
		String classz = feature.GetFieldAsString("CLASS");
		String bz = feature.GetFieldAsString("BZ");
		String slx = feature.GetFieldAsString("SLX");
		Geometry geom = feature.GetGeometryRef();
		//step 1、生成原始wkt
		String wkt = geom.ExportToWkt();
		wkt = "SRID=" + srid +";" + wkt;//拼接srid,实现动态写入
		list.add(new GeographicName(name, pinyin, classz, bz, slx, wkt));
		System.out.println("name=" + name + "tclassz=" + classz+ "twkt="+ wkt);
	}
	geographicNameService.saveBatch(list,300);
	dataSource.delete();
	gdal.GDALDestroyDriverManager();
}

对GeoJSON处理的总结

Java环境下操作GDAL处理GeoJSON矢量数据的过程颇为繁琐,且各步骤紧密相连。首先,通过QGIS进行数据展示;其次,在PostGIS中构建空间数据库;随后,运用GDAL进行数据解析;再之后,构建Java实体模型;最终,将数据存入数据库。每个阶段都要求具备特定的技术知识和操作技巧。相关人员需持续积累经验,以便更高效地处理GeoJSON数据。

package com.yelang.project.extend.earthquake.domain;
import java.io.Serializable;
import com.baomidou.mybatisplus.annotation.TableField;
import com.baomidou.mybatisplus.annotation.TableId;
import com.baomidou.mybatisplus.annotation.TableName;
import com.yelang.framework.handler.PgGeometryTypeHandler;
import lombok.AllArgsConstructor;
import lombok.Data;
import lombok.NoArgsConstructor;
import lombok.ToString;
@Data
@ToString
@AllArgsConstructor
@NoArgsConstructor
@TableName(value ="biz_geographic_name",autoResultMap = true)
public class GeographicName implements Serializable{
	private static final long serialVersionUID = -3694849578429480952L;
	@TableId(value = "pk_id")
	private Long pkId;
	private String name;
	private String pinyin;
	private String classz;
	private String bz;
	private String slx;
	public GeographicName(String name, String pinyin, String classz, String bz, String slx, String geom) {
		super();
		 = name;
		this.pinyin = pinyin;
		this.classz = classz;
		this.bz = bz;
		this.slx = slx;
		this.geom = geom;
	}
	@TableField(typeHandler = PgGeometryTypeHandler.class)
	private String geom;
	@TableField(exist=false)
	private String geomJson;  
}

在处理GeoJSON数据时,你是否也遇到了难题?欢迎在评论区分享你的经历,或者点赞、转发这篇文章。

基于Java和GDAL实现的GeoJSON数据读取与入库实践

发表评论