sql >> データベース >  >> RDS >> Mysql

GormとMySQLを使用した空間データの操作

    別のアプローチがあります。バイナリエンコーディングを使用します。

    これによると、 doc 、MySQLは、SRID(空間参照ID)とそれに続く値のWKB(既知のバイナリ)表現を示すために4バイトを使用してジオメトリ値を格納します。

    したがって、タイプはWKBエンコーディングを使用して、Value()およびScan()関数で4バイトのプレフィックスを追加および削除できます。他の回答にあるgo-geomライブラリには、WKBエンコーディングパッケージgithub.com/twpayne/go-geom/encoding/wkbがあります。

    例:

    type MyPoint struct {
        Point wkb.Point
    }
    
    func (m *MyPoint) Value() (driver.Value, error) {
        value, err := m.Point.Value()
        if err != nil {
            return nil, err
        }
    
        buf, ok := value.([]byte)
        if !ok {
            return nil, fmt.Errorf("did not convert value: expected []byte, but was %T", value)
        }
    
        mysqlEncoding := make([]byte, 4)
        binary.LittleEndian.PutUint32(mysqlEncoding, 4326)
        mysqlEncoding = append(mysqlEncoding, buf...)
    
        return mysqlEncoding, err
    }
    
    func (m *MyPoint) Scan(src interface{}) error {
        if src == nil {
            return nil
        }
    
        mysqlEncoding, ok := src.([]byte)
        if !ok {
            return fmt.Errorf("did not scan: expected []byte but was %T", src)
        }
    
        var srid uint32 = binary.LittleEndian.Uint32(mysqlEncoding[0:4])
    
        err := m.Point.Scan(mysqlEncoding[4:])
    
        m.Point.SetSRID(int(srid))
    
        return err
    }
    

    MyPointタイプを使用したタグの定義:

    type Tag struct {
        Name string   `gorm:"type:varchar(50);primary_key"`
        Loc  *MyPoint `gorm:"column:loc"`
    }
    
    func (t Tag) String() string {
        return fmt.Sprintf("%s @ Point(%f, %f)", t.Name, t.Loc.Point.Coords().X(), t.Loc.Point.Coords().Y())
    }
    

    タイプを使用してタグを作成する:

    tag := &Tag{
        Name: "London",
        Loc: &MyPoint{
            wkb.Point{
                geom.NewPoint(geom.XY).MustSetCoords([]float64{0.1275, 51.50722}).SetSRID(4326),
            },
        },
    }
    
    err = db.Create(&tag).Error
    if err != nil {
        log.Fatalf("create: %v", err)
    }
    

    MySQLの結果:

    mysql> describe tag;
    +-------+-------------+------+-----+---------+-------+
    | Field | Type        | Null | Key | Default | Extra |
    +-------+-------------+------+-----+---------+-------+
    | name  | varchar(50) | NO   | PRI | NULL    |       |
    | loc   | geometry    | YES  |     | NULL    |       |
    +-------+-------------+------+-----+---------+-------+
    
    
    mysql> select name, st_astext(loc) from tag;
    +--------+------------------------+
    | name   | st_astext(loc)         |
    +--------+------------------------+
    | London | POINT(0.1275 51.50722) |
    +--------+------------------------+
    
    • ArcGISによると 4326は、全世界で参照データを格納するための最も一般的な空間参照です。これは、PostGIS空間データベースとGeoJSON標準の両方のデフォルトとして機能します。ほとんどのWebマッピングライブラリでもデフォルトで使用されます。)


    1. MariaDBでのTO_BASE64()のしくみ

    2. SelectQueryでGroupbyを使用してHaving句を適用する方法-SQLServer/TSQLチュートリアルパート131

    3. 戻るボタンを押すと、強制的にリロード/リフレッシュします

    4. caseステートメントを使用して、結合を残すフィールドを決定する方法