banner
biuaxia

biuaxia

"万物皆有裂痕,那是光进来的地方。"
github
bilibili
tg_channel

Consolidating Composition and Forwarding in Golang GPS Program

title: Solving Practical Problems with Golang Latitude and Longitude DMS
date: 2022-05-30 20:56:00
toc: false
index_img: https://puep.qpic.cn/coral/Q3auHgzwzM4fgQ41VTF2rOU6dDf5z5eHjtKaxyHSNLafiaq6Z9sVjzQ/0
category:

  • Go
    tags:
  • Automatic
  • Creation
  • Computation
  • Strings
  • Printing

Problem#

Please write a program that uses the gps structure to represent the Global Positioning System (GPS). This structure should consist of two location structures and one world structure, where the former is used to represent the current and target locations, and the latter is used to represent the world where the locations are located.

Please implement a description method for the location type, which returns a string containing the name, latitude, and longitude. As for the implementation of the world type, please refer to the article:

{post cid="32"}

which mentions the func (w world) distance(p1, p2 location) float64 method.

Please bind two methods to the gps type. The first one is the distance method, which is used to calculate the distance between the current and target locations. The second one is the message method, which describes the distance to the destination in kilometers as a string.

Finally, please create a rover structure and embed gps in it. Then write a main function to test all the functionalities. Please initialize a Global Positioning System for Mars in the test function, set its current location to the Bradbury Landing site (-4.5895, 137.4417), and set the target location to the Elysium Planitia (4.5, 135.9). Then create a curiosity rover and use the message method to print the corresponding information (this method will be forwarded to the same-named method of the gps type).

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{"Bradbury Landing", -4.5895, 137.4417}
	elysium := location{"Elysium Planitia", 4.5, 135.9}

	gps := gps{mars, bradbury, elysium}
	curiosity := rover{gps}
	fmt.Println(curiosity.message())
}

Summary#

  • Composition is a technique for breaking down large structures into smaller ones and combining them together.
  • Embedding allows the outer structure to access the fields of the inner structure.
  • When a type is embedded in a structure, its methods are automatically implemented for forwarding.
  • If multiple embedded types have methods with the same name and these methods are called by the program, Go will prompt for naming conflicts.
Loading...
Ownership of this post data is guaranteed by blockchain and smart contracts to the creator alone.