title: Golang の緯度経度 DMS による実際の問題解決
date: 2022-05-30 20:56:00
toc: false
index_img: https://puep.qpic.cn/coral/Q3auHgzwzM4fgQ41VTF2rOU6dDf5z5eHjtKaxyHSNLafiaq6Z9sVjzQ/0
category:
- Go
tags: - 自動
- 作成
- 計算
- 文字列
- 印刷
問題#
gps
構造体を使用して、全地球測位システム(Global Positioning System、GPS)を表すプログラムを作成してください。この構造体は、現在地と目的地を表す 2 つの location
構造体と、位置が存在する世界を表す 1 つの world
構造体で構成されるべきです。
location
型に description
メソッドを実装してください。このメソッドは、名前、緯度、経度を含む文字列を返すことができます。world
型の実装については、次の記事を参照してください:
{post cid="32"}
func (w world) distance(p1, p2 location) float64
メソッドについて言及されています。
gps
型に 2 つのメソッドをバインドしてください。最初のメソッドは distance
で、現在地と目的地の間の距離を計算します。2 つ目のメソッドは message
で、目的地までの距離を文字列形式で説明します。
最後に、rover
構造体を作成し、その中に gps
を埋め込み、すべての機能をテストするための main
関数を作成してください。テスト関数内で火星の全地球測位システムを初期化し、現在地をブラッドベリー着陸点 (-4.5895, 137.4417)
に設定し、目的地をエリジウム平原 (4.5, 135.9)
に設定します。そして、curiosity
探査機を作成し、message
メソッドを使用して対応する情報を印刷します(このメソッドは gps
型の同名メソッドに転送されます)。
gps.go#
package main
import (
"fmt"
"math"
)
type world struct {
radius float64
}
type location struct {
name string
lat, long float64
}
func (l location) description() string {
return fmt.Sprintf("%v (%.1f°, %.1f°)", l.name, l.lat, l.long)
}
type gps struct {
world world
current location
destination location
}
func (g gps) distance() float64 {
return g.world.distance(g.current, g.destination)
}
func (g gps) message() string {
return fmt.Sprintf("%.1f km to %v", g.distance(), g.destination.description())
}
func (w world) distance(p1, p2 location) float64 {
s1, c1 := math.Sincos(rad(p1.lat))
s2, c2 := math.Sincos(rad(p2.lat))
clong := math.Cos(rad(p1.long - p2.long))
return w.radius * math.Acos(s1*s2+c1*c2*clong)
}
func rad(deg float64) float64 {
return deg * math.Pi / 180
}
type rover struct {
gps
}
func main() {
mars := world{3389.5}
bradbury := location{"ブラッドベリー着陸点", -4.5895, 137.4417}
elysium := location{"エリジウム平原", 4.5, 135.9}
gps := gps{mars, bradbury, elysium}
curiosity := rover{gps}
fmt.Println(curiosity.message())
}
まとめ#
- コンポジションは、大きな構造体を小さな構造体に分解し、それらを組み合わせる技術です。
- 埋め込みにより、外部構造体が内部構造体のフィールドにアクセスできるようになります。
- 型が構造体に埋め込まれると、そのメソッドは自動的に転送されます。
- 複数の埋め込み型が同名のメソッドを持ち、これらのメソッドがプログラムで呼び出された場合、Go 言語は名前の衝突を警告します。