Το Stringer είναι μια διεπαφή για τον καθορισμό της μορφής συμβολοσειράς των τιμών.
Η διεπαφή αποτελείται από μία μόνο μέθοδο String:
type Stringer interface {
String() string
}
Οι τύποι που θέλουν να υλοποιήσουν αυτή τη διεπαφή πρέπει να έχουν μια μέθοδο String() που επιστρέφει μια φιλική προς τον άνθρωπο αναπαράσταση του τύπου ως συμβολοσειρά.
Το πακέτο fmt (και πολλά άλλα) θα αναζητήσει αυτή τη μέθοδο για να μορφοποιήσει και να εκτυπώσει τιμές.
Ας υποθέσουμε ότι δουλεύουμε σε μια εφαρμογή που ασχολείται με γεωγραφικές αποστάσεις, μετρημένες σε διαφορετικές μονάδες.
Έχουμε ορίσει τους τύπους DistanceUnit και Distance ως εξής:
type DistanceUnit int
const (
Kilometer DistanceUnit = 0
Mile DistanceUnit = 1
)
type Distance struct {
number float64
unit DistanceUnit
}
Στο παραπάνω παράδειγμα, τα Kilometer και Mile είναι σταθερές του τύπου DistanceUnit.
Αυτοί οι τύποι δεν υλοποιούν τη διεπαφή Stringer, καθώς τους λείπει η μέθοδος String.
Επομένως, οι συναρτήσεις του fmt θα εκτυπώσουν τις τιμές Distance χρησιμοποιώντας την "προεπιλεγμένη μορφή" της Go:
mileUnit := Mile
fmt.Sprint(mileUnit)
// => 1
// The result is '1' because that is the underlying value of the 'Mile' constant (see constant declarations above)
dist := Distance{number: 790.7, unit: Kilometer}
fmt.Sprint(dist)
// => {790.7 0}
// not a very useful output!
Για να κάνουμε την έξοδο πιο κατατοπιστική, υλοποιούμε τη διεπαφή Stringer για τους τύπους DistanceUnit και Distance, προσθέτοντας μια μέθοδο String σε κάθε τύπο:
func (sc DistanceUnit) String() string {
units := []string{"km", "mi"}
return units[sc]
}
func (d Distance) String() string {
return fmt.Sprintf("%v %v", d.number, d.unit)
}
Οι συναρτήσεις του πακέτου fmt θα καλέσουν αυτές τις μεθόδους όταν μορφοποιούν τιμές Distance:
kmUnit := Kilometer
kmUnit.String()
// => km
mileUnit := Mile
mileUnit.String()
// => mi
dist := Distance{
number: 790.7,
unit: Kilometer,
}
dist.String()
// => 790.7 km