代码拉取完成,页面将自动刷新
package geojson
import (
"encoding/json"
"fmt"
"strings"
)
// Define GeometryType enum
type GeometryType string
const (
PointType GeometryType = "Point"
MultiPointType GeometryType = "MultiPoint"
LineStringType GeometryType = "LineString"
MultiLineStringType GeometryType = "MultiLineString"
PolygonType GeometryType = "Polygon"
MultiPolygonType GeometryType = "MultiPolygon"
// GeometryCollectionType GeometryType = "GeometryCollection" 不支持 GeometryCollection 类型
)
// Define Geometry interface, all geometric types must implement this interface
type Geometry interface {
GetType() GeometryType
GetCoordinates() interface{}
GetWkt() string
}
func UnmarshalGeometry(geometryGeoJson []byte) (GeometryType, interface{}, error) {
var auxGeom struct {
Type string `json:"type"`
Coordinates json.RawMessage `json:"coordinates"`
}
err := json.Unmarshal(geometryGeoJson, &auxGeom)
if err != nil {
return "", nil, err
}
coordRaw := auxGeom.Coordinates
// 根据 Geometry.Type 决定如何解析 Geometry 字段
switch gtype := strings.ToUpper(auxGeom.Type); gtype {
case "POINT":
var coordinates []float64
if err := json.Unmarshal(coordRaw, &coordinates); err != nil {
return "", nil, err
}
point := Point{Type: PointType, Coordinates: coordinates}
return PointType, point, nil
case "LINESTRING":
var coordinates [][]float64
if err := json.Unmarshal(coordRaw, &coordinates); err != nil {
return "", nil, err
}
linestring := LineString{Type: LineStringType, Coordinates: coordinates}
return LineStringType, linestring, nil
case "POLYGON":
var coordinates [][][]float64
if err := json.Unmarshal(coordRaw, &coordinates); err != nil {
return "", nil, err
}
polygon := Polygon{Type: PolygonType, Coordinates: coordinates}
return PolygonType, polygon, nil
case "MULTIPOINT":
var coordinates [][]float64
if err := json.Unmarshal(coordRaw, &coordinates); err != nil {
return "", nil, err
}
mp := MultiPoint{Type: MultiLineStringType, Coordinates: coordinates}
return MultiLineStringType, mp, nil
case "MULTILINESTRING":
var coordinates [][][]float64
if err := json.Unmarshal(coordRaw, &coordinates); err != nil {
return "", nil, err
}
ml := MultiLineString{Type: MultiLineStringType, Coordinates: coordinates}
return MultiLineStringType, ml, nil
case "MULTIPOLYGON":
var coordinates [][][][]float64
if err := json.Unmarshal(coordRaw, &coordinates); err != nil {
return "", nil, err
}
mpg := MultiPolygon{Type: MultiLineStringType, Coordinates: coordinates}
return MultiLineStringType, mpg, nil
default:
return "", nil, fmt.Errorf("unsupported geometry type: %s", auxGeom.Type)
}
}
// Define specific geometry types
type Point struct {
Type GeometryType `json:"type"`
Coordinates []float64 `json:"coordinates"`
}
func (p Point) GetType() GeometryType {
return p.Type
}
func (p Point) GetCoordinates() interface{} {
return p.Coordinates
}
func (p Point) GetWkt() string {
wkt := fmt.Sprintf("POINT(%f %f)", p.Coordinates[0], p.Coordinates[1])
return wkt
}
type MultiPoint struct {
Type GeometryType `json:"type"`
Coordinates [][]float64 `json:"coordinates"`
}
func (m MultiPoint) GetType() GeometryType {
return m.Type
}
func (m MultiPoint) GetCoordinates() interface{} {
return m.Coordinates
}
func (m MultiPoint) GetWkt() string {
coords := []string{}
for _, point := range m.Coordinates {
coord := fmt.Sprintf("%f %f", point[0], point[1])
coords = append(coords, coord)
}
wkt := fmt.Sprintf("MultiPoint(%s)", strings.Join(coords, ","))
return wkt
}
type LineString struct {
Type GeometryType `json:"type"`
Coordinates [][]float64 `json:"coordinates"`
}
func (l LineString) GetType() GeometryType {
return l.Type
}
func (l LineString) GetCoordinates() interface{} {
return l.Coordinates
}
func (l LineString) GetWkt() string {
coords := []string{}
for _, point := range l.Coordinates {
coord := fmt.Sprintf("%f %f", point[0], point[1])
coords = append(coords, coord)
}
wkt := fmt.Sprintf("LineString(%s)", strings.Join(coords, ","))
return wkt
}
type MultiLineString struct {
Type GeometryType `json:"type"`
Coordinates [][][]float64 `json:"coordinates"`
}
func (m MultiLineString) GetType() GeometryType {
return m.Type
}
func (m MultiLineString) GetCoordinates() interface{} {
return m.Coordinates
}
func (m MultiLineString) GetWkt() string {
lines := []string{}
for _, line := range m.Coordinates {
coords := []string{}
for _, point := range line {
coord := fmt.Sprintf("%f %f", point[0], point[1])
coords = append(coords, coord)
}
lines = append(lines, fmt.Sprintf("(%s)", strings.Join(coords, ",")))
}
wkt := fmt.Sprintf("MultiLineString(%s)", strings.Join(lines, ","))
return wkt
}
type Polygon struct {
Type GeometryType `json:"type"`
Coordinates [][][]float64 `json:"coordinates"`
}
func (p Polygon) GetType() GeometryType {
return p.Type
}
func (p Polygon) GetCoordinates() interface{} {
return p.Coordinates
}
func (p Polygon) GetWkt() string {
// Polygon((30 10,40 40,20 40,10 20,30 10),(40 40,30 30,40 20,30 10))
prings := []string{}
for _, ring := range p.Coordinates {
pcoords := []string{}
for _, point := range ring {
coord := fmt.Sprintf("%f %f", point[0], point[1])
pcoords = append(pcoords, coord)
}
prings = append(prings, fmt.Sprintf("(%s)", strings.Join(pcoords, ",")))
}
wkt := fmt.Sprintf("POLYGON(%s)", strings.Join(prings, ","))
return wkt
}
type MultiPolygon struct {
Type GeometryType `json:"type"`
Coordinates [][][][]float64 `json:"coordinates"`
}
func (m MultiPolygon) GetType() GeometryType {
return m.Type
}
func (m MultiPolygon) GetCoordinates() interface{} {
return m.Coordinates
}
func (m MultiPolygon) GetWkt() string {
lines := []string{}
for _, line := range m.Coordinates {
prings := []string{}
for _, ring := range line {
pcoords := []string{}
for _, point := range ring {
coord := fmt.Sprintf("%f %f", point[0], point[1])
pcoords = append(pcoords, coord)
}
prings = append(prings, fmt.Sprintf("(%s)", strings.Join(pcoords, ",")))
}
lines = append(lines, fmt.Sprintf("(%s)", strings.Join(prings, ",")))
}
wkt := fmt.Sprintf("MultiPolygon(%s)", strings.Join(lines, ","))
return wkt
}
// type GeometryCollection struct {
// Type GeometryType `json:"type"`
// Geometries []Geometry `json:"geometries"`
// }
// func (g GeometryCollection) GetType() GeometryType {
// return g.Type
// }
// func (g GeometryCollection) GetCoordinates() interface{} {
// return g.Geometries
// }
此处可能存在不合适展示的内容,页面不予展示。您可通过相关编辑功能自查并修改。
如您确认内容无涉及 不当用语 / 纯广告导流 / 暴力 / 低俗色情 / 侵权 / 盗版 / 虚假 / 无价值内容或违法国家有关法律法规的内容,可点击提交进行申诉,我们将尽快为您处理。