Διαδρομές
/
R
R
/
Ασκήσεις
/
Ανάμεικτοι χυμοί
Ανάμεικτοι χυμοί

Ανάμεικτοι χυμοί

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

Εισαγωγή

Υπάρχουν βασικά δύο τύποι βρόχων:

  1. Επανάληψη μέχρι να ικανοποιηθεί μια συνθήκη.
  2. Επανάληψη πάνω από τα στοιχεία μιας συλλογής.

Και οι δύο είναι εφικτοί στην R, αν και ο πρώτος μπορεί να είναι πιο συνηθισμένος.

while και repeat

Για προβλήματα ανοιχτού τύπου, όπου ο αριθμός των περασμάτων από τον βρόχο δεν είναι γνωστός εκ των προτέρων, η R έχει τον while βρόχο με συνθήκη και τον repeat βρόχο χωρίς συνθήκη (ισοδύναμο με while (TRUE)).

Η βασική μορφή είναι αρκετά απλή:

while (condition) {
  do_something()
}

Σε αυτή την περίπτωση, το πρόγραμμα θα συνεχίσει να κάνει περάσματα από τον βρόχο μέχρι η condition να μην είναι πια TRUE.

Υπάρχουν δύο τρόποι να βγεις νωρίς από τον βρόχο:

  • Ένα break προκαλεί την έξοδο από τον βρόχο, με την εκτέλεση να συνεχίζεται στην επόμενη γραμμή μετά το άγκιστρο κλεισίματος } του βρόχου.
  • Ένα return(x) σταματά την εκτέλεση της τρέχουσας συνάρτησης και περνά την τιμή επιστροφής x πίσω σε όποιον κάλεσε τη συνάρτηση.

Με αυτές τις επιλογές διαθέσιμες, μερικές φορές μπορεί να σε βολέψει να δημιουργήσεις έναν "άπειρο" βρόχο με repeat { ... } και μετά να βασιστείς στο ότι θα βρεις μια συνθήκη τερματισμού μέσα στο σώμα του βρόχου, ώστε να προκαλέσεις ένα break ή ένα return.

Αυτές οι τρεις παραλλαγές είναι ισοδύναμες και όλες τελειώνουν με x == 0.4444...

x <- 12
while (x > 1) {
  x <- x / 3
}

x <- 12
while (TRUE) {
  x <- x/3
  if (x <= 1) break
}

x <- 12
# no boolean clause 
repeat { 
  x <- x/3
  if (x <= 1) break
}

Επανάληψη πάνω από ένα διάνυσμα

Αυτό συχνά δεν είναι απαραίτητο στην R. Όπως έχει συζητηθεί και σε άλλες έννοιες, πολλές συναρτήσεις λειτουργούν σε ολόκληρα διανύσματα.

Ωστόσο, μερικές φορές οι ρητοί βρόχοι είναι αναπόφευκτοι. Αυτό ισχύει ειδικά όταν:

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

Η συνθήκη του βρόχου πρέπει να είναι μέσα σε παρενθέσεις. Όπως και με τα σώματα των συναρτήσεων, τα άγκιστρα είναι προαιρετικά (αν και συχνά περιλαμβάνονται) για σώματα βρόχου μιας γραμμής.

words <- c("This", "is", "a", "loop")
for (w in words) { print(w) } # the braces are optional here
#> [1] "This"
#> [1] "is"
#> [1] "a"
#> [1] "loop"

Αν η τρέχουσα επανάληψη δεν ικανοποιεί κάποια συνθήκη, μπορείς να μεταβείς αμέσως στην επόμενη επανάληψη με ένα next:

for (n in 1:10) {
    if (is_useless(n)) next
     
    # we decided this iteration could be useful
    do_something_slow(n)
}

Αν χρειάζεσαι την αριθμητική θέση, χρησιμοποίησε το seq_along().

v <- LETTERS[1:3]
v
#> [1] "A" "B" "C"

for (i in seq_along(v)) { print(sprintf("%s%i", v[i], i)) }
#> [1] "A1"
#> [1] "B2"
#> [1] "C3"

Η χρήση του i in 1:length(v) δεν συνιστάται, καθώς μπορεί να προκαλέσει προβλήματα όταν το length(v) είναι μηδέν. Το διάστημα 1:0 είναι ισοδύναμο με το c(1, 0), οπότε το σώμα του βρόχου θα εκτελεστεί και πιθανότατα θα αποτύχει. Η συνάρτηση seq_along() είναι σχεδιασμένη να χειρίζεται σωστά αυτή την περίπτωση.

Οδηγίες

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

1. Υπολόγισε πόσο χρόνο χρειάζεται για να αναμείξεις έναν χυμό

Στη Li Mei αρέσει να λέει στους πελάτες της εκ των προτέρων πόσο θα περιμένουν για τον χυμό από το μενού που παρήγγειλαν. Δυσκολεύεται να θυμάται τους ακριβείς αριθμούς, γιατί ο χρόνος ανάμειξης των χυμών ποικίλλει. Το "Pure Strawberry Joy" χρειάζεται 0,5 λεπτά, το "Energizer" και το "Green Garden" χρειάζονται 1,5 λεπτά το καθένα, το "Tropical Island" χρειάζεται 3 λεπτά και το "All or Nothing" χρειάζεται 5 λεπτά. Για όλα τα άλλα ροφήματα (π.χ. προσφορές) μπορείς να υποθέσεις χρόνο προετοιμασίας 2,5 λεπτά.

Για να βοηθήσεις τη φίλη σου, γράψε μια συνάρτηση time_to_mix_juice που παίρνει ως όρισμα έναν χυμό από το μενού και επιστρέφει τον αριθμό των λεπτών που χρειάζεται για να αναμειχθεί αυτό το ρόφημα.

time_to_mix_juice("Tropical Island")
# => 3

time_to_mix_juice("Berries & Lime")
# => 2.5

2. Ανανέωσε το απόθεμα από φέτες λάιμ

Πολλές από τις δημιουργίες της Li Mei περιλαμβάνουν φέτες λάιμ, είτε ως συστατικό είτε ως μέρος της διακόσμησης. Έτσι, όταν ξεκινά τη βάρδιά της το πρωί, πρέπει να βεβαιωθεί ότι το κουτί με τις φέτες λάιμ είναι γεμάτο για την ημέρα που ακολουθεί.

Υλοποίησε τη συνάρτηση limes_to_cut, η οποία παίρνει τον αριθμό των φετών λάιμ που χρειάζεται να κόψει η Li Mei και έναν πίνακα που αντιπροσωπεύει το απόθεμα από ολόκληρα λάιμ που έχει διαθέσιμα. Μπορεί να πάρει 6 φέτες από ένα λάιμ "small", 8 φέτες από ένα λάιμ "medium" και 10 από ένα λάιμ "large". Κόβει πάντα τα λάιμ με τη σειρά που εμφανίζονται στη λίστα, ξεκινώντας από το πρώτο στοιχείο. Συνεχίζει μέχρι να φτάσει στον αριθμό των φετών που χρειάζεται ή μέχρι να τελειώσουν τα λάιμ.

Η Li Mei θα ήθελε να ξέρει εκ των προτέρων πόσα λάιμ χρειάζεται να κόψει. Η συνάρτηση limes_to_cut πρέπει να επιστρέφει τον αριθμό των λάιμ που πρέπει να κοπούν.

limes_to_cut(25, c("small", "small", "large", "medium", "small"))
# => 4

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

Στη Li Mei αρέσει να παρακολουθεί σε μια οθόνη πόση ώρα θα χρειαστεί για να αναμειχθούν οι παραγγελίες που περιμένουν οι πελάτες.

Υλοποίησε τη συνάρτηση order_times, η οποία παίρνει μια ουρά παραγγελιών και εκτυπώνει στο stdout τον χρόνο που χρειάζεται για να φτιαχτεί η καθεμία.

order_times(c("Energizer", "Tropical Island"))
# => 1.5 
# => 3
Note

Αυτή η εργασία είναι αρκετά ασυνήθιστη για το Exercism, καθώς απαιτεί εκτύπωση στο stdout. Η συντριπτική πλειονότητα των ασκήσεων στο Exercism απαιτεί μια τιμή επιστροφής ή/και κάποια άλλη παρενέργεια.

4. Τελείωσε τη βάρδια

Η Li Mei δουλεύει πάντα μέχρι τις 3 μ.μ. Μετά αναλαμβάνει ο υπάλληλός της, ο Dmitry. Υπάρχουν συχνά ροφήματα που έχουν παραγγελθεί αλλά δεν έχουν ετοιμαστεί ακόμη όταν τελειώνει η βάρδια της Li Mei. Τότε ο Dmitry ετοιμάζει τους υπόλοιπους χυμούς.

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

Ο χρόνος που απομένει στη βάρδια θα είναι πάντα μεγαλύτερος από 0. Ο πίνακας με τους χυμούς προς ετοιμασία δεν θα είναι ποτέ κενός. Επιπλέον, οι παραγγελίες ετοιμάζονται με τη σειρά που εμφανίζονται στον πίνακα. Αν η Li Mei αρχίσει να αναμειγνύει κάποιον χυμό, θα τον τελειώσει πάντα, ακόμη κι αν χρειαστεί να δουλέψει λίγο παραπάνω. Αν δεν έχουν απομείνει παραγγελίες για τις οποίες πρέπει να φροντίσει ο Dmitry, πρέπει να επιστραφεί ένα κενό διάνυσμα.

remaining_orders(5, c("Energizer", "All or Nothing", "Green Garden"))
# => c("Green Garden")
Επεξεργασία μέσω GitHub Ο σύνδεσμος ανοίγει σε νέο παράθυρο ή καρτέλα
R Exercism

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

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