Διαδρομές
/
Go
Go
/
Ασκήσεις
/
Αίθουσα ταξινόμησης
Αίθουσα ταξινόμησης

Αίθουσα ταξινόμησης

Άσκηση εκμάθησης

Εισαγωγή

Μετατροπή τύπων

Η Go απαιτεί ρητή μετατροπή μεταξύ διαφορετικών τύπων. Η μετατροπή μεταξύ τύπων (γνωστή και ως casting τύπων) γίνεται μέσω μιας συνάρτησης με το όνομα του τύπου στον οποίο θέλεις να μετατρέψεις. Για παράδειγμα, για να μετατρέψεις ένα int σε float64, θα χρειαστεί να κάνεις το εξής:

var x int = 42 // x has type int
f := float64(x) // f has type float64 (ie. 42.0)

Μετατροπή μεταξύ πρωτογενών τύπων και συμβολοσειρών

Υπάρχει ένα πακέτο strconv για τη μετατροπή μεταξύ πρωτογενών τύπων (όπως int) και string.

import "strconv"

var intString string = "42"
var i, err = strconv.Atoi(intString)

var number int = 12
var s string = strconv.Itoa(number)

Ισχυρισμοί τύπων

Οι διεπαφές στη Go μπορούν να προκαλέσουν ασάφεια σχετικά με τον υποκείμενο τύπο. Ένας ισχυρισμός τύπου μάς επιτρέπει να εξαγάγουμε τη συγκεκριμένη υποκείμενη τιμή μιας τιμής διεπαφής χρησιμοποιώντας αυτή τη σύνταξη: interfaceVariable.(concreteType).

Για παράδειγμα:

var input any = 12
number := input.(int)

ΣΗΜΕΙΩΣΗ: αυτό θα προκαλέσει panic αν η μεταβλητή διεπαφής δεν περιέχει τιμή του συγκεκριμένου τύπου.

Μπορούμε να ελέγξουμε αν μια τιμή διεπαφής περιέχει έναν συγκεκριμένο τύπο, αξιοποιώντας και τις δύο τιμές επιστροφής του ισχυρισμού τύπου: την υποκείμενη τιμή και μια λογική τιμή που αναφέρει αν ο ισχυρισμός πέτυχε. Για παράδειγμα:

str, ok := input.(string) // no panic if input is not a string

Αν το input περιέχει ένα string, τότε το str θα είναι η υποκείμενη τιμή και το ok θα είναι αληθές. Αν το input δεν περιέχει ένα string, τότε το str θα είναι η μηδενική τιμή του τύπου string (δηλ. "" - η κενή συμβολοσειρά) και το ok θα είναι ψευδές. Δεν προκαλείται panic σε καμία περίπτωση.

Διακόπτες τύπων

Ένας διακόπτης τύπων μπορεί να εκτελέσει αρκετούς ισχυρισμούς τύπων σε σειρά. Έχει την ίδια σύνταξη με έναν ισχυρισμό τύπου (interfaceVariable.(concreteType)), αλλά το concreteType αντικαθίσταται από τη λέξη-κλειδί type. Ακολουθεί ένα παράδειγμα:

var i any = 12 // try: 12.3, true, int64(12), []int{}, map[string]int{}

switch v := i.(type) {
case int:
    fmt.Printf("the integer %d\n", v)
case string:
    fmt.Printf("the string %s\n", v)
default:
    fmt.Printf("type, %T, not handled explicitly: %#v\n", v, v)
}

Οδηγίες

Η Jen εργάζεται στο δωμάτιο διαλογής σε ένα μεγάλο εργοστάσιο. Το δωμάτιο διαλογής πρέπει να επεξεργάζεται ό,τι φτάνει σε αυτό, κατηγοριοποιώντας το με μια ετικέτα. Η Jen είναι υπεύθυνη για πράγματα που έχουν προκατηγοριοποιηθεί ως αριθμοί και χρειάζεται ένα πρόγραμμα που θα τη βοηθήσει στη διαλογή.

Οι περισσότερες πρωτογενείς τιμές πρέπει να παίρνουν απλές ετικέτες. Για τους αριθμούς, θέλει συμβολοσειρές που να λένε "This is the number 2.0" (αν ο αριθμός ήταν 2). Η Jen θέλει την ίδια έξοδο για ακέραιους και δεκαδικούς.

Υπάρχουν μερικές διεπαφές Box που πρέπει να ξετυλιχτούν για να πάρουμε το περιεχόμενό τους. Για ένα NumberBox, θέλει συμβολοσειρές που να λένε "This is a box containing the number 3.0" (αν η μέθοδος Number() επιστρέφει 3). Για ένα FancyNumberBox, θέλει συμβολοσειρές που να λένε "This is a fancy box containing the number 4.0", αλλά μόνο αν ο τύπος είναι FancyNumber.

Οτιδήποτε απρόσμενο πρέπει να λέει "Return to sender", ώστε η Jen να μπορεί να το στείλει πίσω από όπου ήρθε.

1. Περιγράψε τους απλούς αριθμούς

Η Jen θέλει οι αριθμοί να επιστρέφουν συμβολοσειρές όπως "This is the number 2.0" (συμπεριλαμβανομένου ενός ψηφίου μετά την υποδιαστολή):

fmt.Println(DescribeNumber(-12.345))
// Output: This is the number -12.3

2. Περιγράψε ένα κουτί αριθμού

Η Jen θέλει τα κουτιά αριθμών να επιστρέφουν συμβολοσειρές όπως "This is a box containing the number 2.0" (και πάλι, συμπεριλαμβανομένου ενός ψηφίου μετά την υποδιαστολή):

fmt.Println(DescribeNumberBox(numberBoxContaining{12}))
// Output: This is a box containing the number 12.0

3. Υλοποίησε μια μέθοδο που εξάγει τον αριθμό από ένα φανταχτερό κουτί αριθμού

Η Jen χρειάζεται μια βοηθητική συνάρτηση για να εξάγει τον αριθμό από ένα FancyNumberBox. Αν το FancyNumberBox είναι ένα FancyNumber, εξήγαγε την τιμή του και μετέτρεψέ την από string σε int. Κάθε άλλος τύπος FancyNumberBox πρέπει να επιστρέφει 0.

fmt.Println(ExtractFancyNumber(FancyNumber{"10"}))
// Output: 10
fmt.Println(ExtractFancyNumber(AnotherFancyNumber{"4"}))
// Output: 0

4. Περιγράψε ένα φανταχτερό κουτί αριθμού

Αν το FancyNumberBox είναι ένα FancyNumber, η Jen θέλει συμβολοσειρές που να λένε "This is a fancy box containing the number 4.0". Κάθε άλλος τύπος FancyNumberBox πρέπει να λέει "This is a fancy box containing the number 0.0".

fmt.Println(DescribeFancyNumberBox(FancyNumber{"10"}))
// Output: This is a fancy box containing the number 10.0
fmt.Println(DescribeFancyNumberBox(AnotherFancyNumber{"4"}))
// Output: This is a fancy box containing the number 0.0

ΣΗΜΕΙΩΣΗ: πρέπει να χρησιμοποιήσουμε τη συνάρτηση ExtractFancyNumber!

5. Υλοποίησε τη συνάρτηση DescribeAnything που τις χρησιμοποιεί όλες

Αυτή είναι η κύρια συνάρτηση που χρειάζεται η Jen και δέχεται οποιαδήποτε είσοδο. Η DescribeAnything πρέπει να αναθέτει στις άλλες συναρτήσεις με βάση τον τύπο της τιμής που περνάει ως όρισμα. Πιο συγκεκριμένα:

  • Τα int και float64 πρέπει και τα δύο να αναθέτουν στη DescribeNumber
  • Το NumberBox πρέπει να αναθέτει στη DescribeNumberBox
  • Το FancyNumberBox πρέπει να αναθέτει στη DescribeFancyNumberBox
  • οτιδήποτε άλλο πρέπει να έχει ως αποτέλεσμα "Return to sender"
fmt.Println(DescribeAnything(numberBoxContaining{12.345}))
// Output: This is a box containing the number 12.3
fmt.Println(DescribeAnything("some string"))
// Output: Return to sender
Επεξεργασία μέσω GitHub Ο σύνδεσμος ανοίγει σε νέο παράθυρο ή καρτέλα
Go Exercism

Έτοιμος να ξεκινήσεις την άσκηση Αίθουσα ταξινόμησης;

Γράψου στο Exercism για να μάθεις και να κατακτήσεις Go με 34 έννοιες165 ασκήσεις και πραγματική καθοδήγηση από ανθρώπους, όλα δωρεάν.