INTRODUCTION
Καλώς ήρθατε στο σημερινό δωρεάν μάθημα Python! Σαν πρώτο βήμα, θα ξεκινήσουμε ορίζοντας τι ακριβώς είναι ένα function (συνάρτηση) και θα εξηγήσουμε γιατί τα functions αποτελούν απαραίτητα και αναπόσπαστα δομικά στοιχεία του κώδικά μας.
Σε αυτό το μάθημα θα καλύψουμε τα εξής:
- Τι είναι τα functions: Ορισμός και η βασική τους χρησιμότητα.
- Σύνταξη και Δομή: Πώς γράφουμε σωστά ένα function και ποια είναι η συνηθισμένη μορφή που ακολουθεί στην Python.
- Πρακτικά Παραδείγματα: Θα παρουσιάσουμε αναλυτικά παραδείγματα, τα οποία καλύπτουν σχεδόν όλες τις περιπτώσεις που πρόκειται να συναντήσετε σε ένα πραγματικό πρόγραμμα Python.
Σημείωση: Το σημερινό δωρεάν μάθημα αποτελεί το πρώτο μέρος της αναλυτικής μας σειράς πάνω στα functions.
Γιατί Χρειαζόμαστε τα Functions
Πριν εξετάσουμε τη δομή και το συντακτικό ενός function, ας δούμε ένα απλό, πρακτικό παράδειγμα, αξιοποιώντας τις γνώσεις που έχουμε αποκτήσει μέχρι στιγμής στο μάθημα.
Ας υποθέσουμε ότι θέλουμε να δημιουργήσουμε μια απλή εφαρμογή η οποία υπολογίζει τον μισθό ενός εργαζόμενου με βάση τις ώρες που έχει εργαστεί. Με τα εργαλεία που γνωρίζουμε μέχρι τώρα (δηλαδή γράφοντας τον κώδικα "γραμμικά", χωρίς functions), το πρόγραμμα που θα αναπτύσσαμε θα ήταν το εξής:
app.py
Output
Ας προχωρήσουμε ένα βήμα παραπέρα. Υποθέστε τώρα πως στο ίδιο πρόγραμμα θέλουμε να προσθέσουμε και τον υπολογισμό του φόρου που υποχρεούται να πληρώσει ο εργαζόμενος.
Για να ενσωματώσουμε αυτόν τον έξτρα κώδικα, αναγκαζόμαστε να διαβάσουμε όλο το πρόγραμμα από την αρχή, γραμμή προς γραμμή. Αυτό είναι απαραίτητο για να κατανοήσουμε τη ροή του και να εντοπίσουμε το ακριβές σημείο όπου πρέπει να γίνει η νέα προσθήκη.
Ο κώδικάς μας πλέον θα έμοιαζε κάπως έτσι:
app.py
hours = int(input('Hours worked: '))hourly_rate = float(input('Hourly rate: '))salary = hours * hourly_ratetaxes = (salary * 30) / 100payment = salary - taxesprint('Your salary is ', salary)print('Your taxes is ', taxes)print('You will get paid the amount of', payment)
Output
Οι Παγίδες του Αδόμητου Κώδικα
Αναλύοντας το παραπάνω παράδειγμα, παρατηρούμε ότι κάθε φορά που προκύπτει η ανάγκη να προσθέσουμε μια καινούργια λειτουργία, ο κώδικάς μας μεγαλώνει χωρίς να ακολουθεί μια συγκεκριμένη δομή. Απλά προσθέτουμε επιπλέον γραμμές για να υλοποιήσουμε την εκάστοτε ανάγκη.
Αυτή η προσέγγιση δημιουργεί τρία βασικά προβλήματα όταν ενσωματώνεται σε ένα μεγαλύτερο πρόγραμμα:
- Δυσκολία στην ανάγνωση: Πρέπει να διαβάσουμε όλο τον κώδικα από την αρχή για να εντοπίσουμε πού ακριβώς γίνεται ένας συγκεκριμένος υπολογισμός (όπως π.χ. ο υπολογισμός του μισθού).
- Επανάληψη κώδικα: Αν χρειαστεί να επαναλάβουμε τον ίδιο υπολογισμό σε διαφορετικό σημείο κατά την εκτέλεση του προγράμματος, αναγκαζόμαστε να ξαναγράψουμε ακριβώς τις ίδιες γραμμές. Το πρόγραμμά μας καταλήγει να περιέχει τον ίδιο κώδικα γραμμένο πολλαπλές φορές.
- Πρόβλημα επεκτασιμότητας: Αυτός ο τρόπος ανάπτυξης θα σας προκαλέσει τεράστιο πονοκέφαλο όταν η εφαρμογή σας αρχίσει να μεγαλώνει και να προσφέρει περισσότερες υπηρεσίες στον τελικό χρήστη.
Τι είναι λοιπόν ένα Function;
Με απλά λόγια, ένα function (συνάρτηση) είναι η ομαδοποίηση γραμμών κώδικα που προσφέρουν μια συγκεκριμένη υπηρεσία ή εκτελούν μια συγκεκριμένη εργασία.
Για παράδειγμα, όλος ο υπολογισμός του μισθού θα μπορούσε να είναι «πακεταρισμένος» μέσα σε ένα function. Έτσι, όταν θέλουμε να εκτελέσουμε τη συγκεκριμένη εργασία, απλά καλούμε το όνομα του function και εκείνο αναλαμβάνει να εκτελέσει με τη σειρά τον κώδικα που περιέχει.
Σκεφτείτε πόσο πιο εύκολο θα είναι να διορθώσετε ή να επεκτείνετε τον κώδικά σας, αν αντί για αυτό:
έχετε οργανώσει τον κώδικα σας με functions.
Με αυτή την απλή αλλαγή, η συνολική αρχιτεκτονική του προγράμματός σας αναβαθμίζεται ριζικά. Πιο συγκεκριμένα:
- Άριστη Οργάνωση Κώδικα: Ο κώδικας της εφαρμογής σας αποκτά δομή. Αντί για ένα ατελείωτο "κατεβατό" από γραμμές, έχετε ξεκάθαρα τμήματα. Έτσι, μπορείτε πολύ εύκολα να εντοπίσετε τις συγκεκριμένες υπηρεσίες ή λειτουργίες που θέλετε να αναβαθμίσετε στο μέλλον.
- Αποφυγή Επαναλήψεων: Αυτό είναι ίσως το πιο σημαντικό πλεονέκτημα. Αποφεύγετε να αναπαράγετε τον ίδιο ακριβώς κώδικα ξανά και ξανά. Γράφετε τη λογική μία φορά (μέσα στο function) και απλά την καλείτε όποτε τη χρειάζεστε.
- Ευκολότερος Έλεγχος (Testing): Όταν η λογική της εφαρμογής σας είναι "σπασμένη" σε μικρά, ανεξάρτητα κομμάτια (functions), μπορείτε πολύ πιο εύκολα να τεστάρετε το καθένα ξεχωριστά για να βεβαιωθείτε ότι η εφαρμογή σας λειτουργεί απολύτως σωστά.
Πώς Ορίζουμε και Καλούμε ένα Function
Για να δημιουργήσουμε ένα function, το πρώτο βήμα είναι να του δώσουμε ένα όνομα. Οι κανόνες ονομασίας ενός function είναι ακριβώς οι ίδιοι με εκείνους που χρησιμοποιούμε για να ονομάσουμε τις μεταβλητές. Πιο συγκεκριμένα:
- Δεσμευμένες λέξεις: Δεν μπορούμε να χρησιμοποιήσουμε ένα όνομα που ήδη χρησιμοποιεί η Python ως λέξη-κλειδί (π.χ.
print,if,while). - Κενά διαστήματα: Το όνομα δεν επιτρέπεται να περιέχει κενά. Συνήθως χρησιμοποιούμε την κάτω παύλα ( _ ) για να ενώσουμε λέξεις (π.χ.
ypologismos_misthou). - Αρχικός χαρακτήρας: Ο πρώτος χαρακτήρας πρέπει υποχρεωτικά να είναι γράμμα ή κάτω παύλα ( _ ), και όχι αριθμός.
Η Βασική Δομή (Σύνταξη)
Η γενική δομή για να δημιουργήσουμε ένα function στην Python είναι η εξής:
Python
def function_name(): statement 1 # Εντολή 1 statement 2 # Εντολή 2
Πώς Καλούμε (Εκτελούμε) ένα Function
Ας αναλύσουμε τα στοιχεία αυτής της δομής:
- Η λέξη-κλειδί
def: Πριν από το όνομα του function, προσθέτουμε τη λέξηdef(από το define). Έτσι, η Python καταλαβαίνει ότι πρόκειται να ορίσουμε ένα νέο function. - Το όνομα και οι παρενθέσεις
(): Το όνομα του function ακολουθείται πάντα από παρενθέσεις. Μέσα σε αυτές, μπορούμε προαιρετικά να ορίσουμε παραμέτρους (δεδομένα που θα χρησιμοποιήσει το function στις πράξεις του). - Η άνω και κάτω τελεία
:Η πρώτη γραμμή του ορισμού κλείνει υποχρεωτικά με άνω και κάτω τελεία. - Ο κώδικας (Εσοχή / Indentation): Αμέσως μετά, ακολουθεί ο κώδικας που θέλουμε να περιέχει το function. Προσέξτε ότι αυτές οι γραμμές πρέπει να έχουν ένα κενό (εσοχή) προς τα μέσα, για να γνωρίζει η Python ότι ανήκουν στο συγκεκριμένο function.
Αφού δημιουργήσουμε ένα function, αυτό δεν εκτελείται από μόνο του. Για να το βάλουμε να δουλέψει, απλά γράφουμε το όνομά του ακολουθούμενο από παρενθέσεις στο σημείο του κώδικα που το χρειαζόμαστε.
Ας δούμε ένα πολύ απλό παράδειγμα στην πράξη:
app.py
def favorite_team():print('Everyone has a favorite soccer team')print('mine is Barcelona')favorite_team()
Output
Από τη στιγμή που έχετε ορίσει ένα function μια φορά, μπορείτε να το καλέσετε όσες φορές θέλετε.
app.py
def favorite_team():print('Everyone has a favorite soccer team')print('mine is Barcelona')favorite_team()favorite_team()favorite_team()
Output
Όταν τα Functions Καλλούν Άλλα Functions (Η δομή main)
Ένα από τα πιο ισχυρά χαρακτηριστικά του προγραμματισμού είναι ότι ένα function μπορεί να καλέσει άλλα functions. Δεν περιοριζόμαστε στο να τα καλούμε μόνο από τον "χύμα" (global) κώδικα.
Στην πράξη, ο πιο συνηθισμένος και επαγγελματικός τρόπος οργάνωσης ενός προγράμματος είναι να δημιουργούμε ένα κεντρικό, κύριο function. Παραδοσιακά, στην κοινότητα των προγραμματιστών αυτό το ονομάζουμε main (φυσικά, μπορείτε να του δώσετε όποιο όνομα θέλετε).
Ο ρόλος του main function είναι να λειτουργεί ως ο "διευθυντής ορχήστρας": είναι το function που ξεκινάει πρώτο, καλεί τα υπόλοιπα functions με τη σωστή σειρά, συντονίζει την εκτέλεσή τους και ολοκληρώνει το πρόγραμμα.
Δείτε πώς φαίνεται αυτό σε κώδικα:
app.py
def main():message()favorite_team()def message():print('Everyone has a favorite team')def favorite_team():print('mine is Barcelona')main()
Output
Όταν γράφουμε functions στην Python, πρέπει να δώσουμε τεράστια προσοχή στο indentation (δηλαδή στις εσοχές ή τα κενά διαστήματα στην αρχή της γραμμής).
Οι γραμμές κώδικα που ανήκουν στο εσωτερικό ενός function θα πρέπει υποχρεωτικά να έχουν ένα κενό διάστημα στην αρχή τους (συνήθως 1 Tab ή 4 spaces). Αυτός είναι ο μοναδικός τρόπος για να αναγνωρίσει η Python ποιες εντολές ανήκουν στο function και ποιες αποτελούν μέρος του κύριου προγράμματος.
Την ίδια ακριβώς λογική έχουμε ήδη συναντήσει στα if...else statements και στα loops (επαναλήψεις), οπότε η έννοια αυτή δεν σας είναι άγνωστη!
Η Λέξη-Κλειδί pass: Το Απόλυτο "Placeholder"
Πολλές φορές, κατά τα αρχικά στάδια ανάπτυξης (όταν σχεδιάζουμε τον σκελετό μιας εφαρμογής), γνωρίζουμε εκ των προτέρων ποια functions θα χρειαστούμε και πώς θα τα ονομάσουμε, αλλά δεν είμαστε ακόμα έτοιμοι να γράψουμε τις λεπτομέρειες του κώδικά τους.
Επειδή η Python απαιτεί υποχρεωτικά να υπάρχει έστω και μία γραμμή κώδικα κάτω από τον ορισμό ενός function, αν το αφήσουμε εντελώς άδειο, το πρόγραμμα θα μας "πετάξει" σφάλμα. Σε αυτές ακριβώς τις περιπτώσεις χρησιμοποιούμε τη λέξη-κλειδί pass.
Πώς λειτουργεί στην πράξη:
- Αποφυγή Σφαλμάτων: Μπορείτε να ορίσετε τα functions σας και, αντί για πραγματικό κώδικα, να γράψετε απλώς τη λέξη
pass. Η Python θα αναγνωρίσει τη δομή και θα εκτελέσει το πρόγραμμα κανονικά, χωρίς να σας παρουσιάσει κανένα λάθος στο terminal. - Αόρατη Εκτέλεση: Φυσικά, αν καλέσετε αυτό το function, δεν θα δείτε κάποιο αποτέλεσμα στην οθόνη, ακριβώς επειδή δεν περιέχει λειτουργικό κώδικα. Λειτουργεί καθαρά ως "κράτηση χώρου" (placeholder).
- Σταδιακή Ανάπτυξη: Αργότερα, όταν έχετε σκεφτεί όλες τις λεπτομέρειες και είστε έτοιμοι να αναπτύξετε τη λειτουργία, απλά επιστρέφετε στο function, διαγράφετε τη λέξη
passκαι την αντικαθιστάτε με τον πραγματικό σας αλγόριθμο.
Δείτε πώς φαίνεται ένα πρόγραμμα που βρίσκεται σε φάση σχεδιασμού:
app.py
def main():message()favorite_team()def message():passdef favorite_team():print('mine is Barcelona')main()
Output
Τοπικές Μεταβλητές (Local Variables) και Εμβέλεια
Καθώς γράφουμε τον κώδικα ενός function, είναι απόλυτα φυσιολογικό να δημιουργούμε νέες μεταβλητές στο εσωτερικό του για να εξυπηρετήσουμε τους υπολογισμούς μας. Το πιο σημαντικό χαρακτηριστικό αυτών των μεταβλητών είναι ότι έχουν τοπική εμβέλεια (local scope).
Τι ακριβώς σημαίνει αυτό στην πράξη;
- Περιορισμένη Πρόσβαση: Μόνο ο κώδικας που βρίσκεται μέσα στο ίδιο το function έχει πρόσβαση σε αυτές τις μεταβλητές και μπορεί να τις χρησιμοποιήσει.
- Είναι "Αόρατες" στους Υπόλοιπους: Άλλα functions ή ο κώδικας από το κύριο μέρος της εφαρμογής (το κυρίως πρόγραμμα) δεν μπορούν να «δουν» αυτές τις τοπικές μεταβλητές. Κατά συνέπεια, είναι αδύνατον να τις καλέσουν ή να τροποποιήσουν την τιμή τους.
Για να γίνει απολύτως κατανοητό, ας δούμε ένα παράδειγμα:
app.py
def main():message()favorite_team()def message():print('Everyone has a favorite team')def favorite_team():team = 'Barcelona'print('mine is', team)main()
Output
Περνώντας Δεδομένα στα Functions (Arguments & Parameters)
Η πραγματική δύναμη και χρησιμότητα ενός function δεν περιορίζεται μόνο στο ότι αποφεύγουμε την επανάληψη του ίδιου κώδικα. Η μαγεία τους κρύβεται στη δυνατότητά τους να δέχονται εξωτερικές τιμές (δεδομένα) και να προσαρμόζουν τη λειτουργία τους ανάλογα. Αυτό γίνεται μέσω των παραμέτρων (parameters).
Για να μπορέσει ένα function να δεχτεί τιμές, θα πρέπει κατά τη δημιουργία του να ορίσουμε μία ή περισσότερες μεταβλητές ως παραμέτρους.
- Πού ορίζονται; Ο ορισμός των parameters γίνεται πάντα μέσα στις παρενθέσεις δίπλα από το όνομα του function.
- Πώς τις χρησιμοποιούμε; Όταν καλούμε το function στο κυρίως πρόγραμμα, απλά γράφουμε μέσα στην παρένθεση τις πραγματικές τιμές (γνωστές ως arguments) που θέλουμε να του "περάσουμε".
Προσοχή: Ο κανόνας είναι ότι πρέπει να περάσουμε ακριβώς τόσες τιμές όσες είναι και οι parameters που έχουμε ορίσει!
Ας δούμε ένα απλό παράδειγμα για να γίνει ξεκάθαρο:
app.py
def main():message()favorite_team('Barcelona')def message():print('Everyone has a favorite team')def favorite_team(team):print('mine is', team)main()
Output
Προεπιλεγμένες Τιμές Παραμέτρων (Default Values)
Μπορούμε, αν θέλουμε, να προκαθορίσουμε την τιμή που θα πάρει μια παράμετρος, σε περίπτωση που δεν δοθεί κάποια τιμή κατά την κλήση του function. Με άλλα λόγια, μπορούμε να ορίσουμε μια default value (προεπιλεγμένη τιμή).
Ο κανόνας για τις προεπιλεγμένες τιμές είναι πολύ απλός:
- Εάν περάσουμε εμείς κάποια δική μας τιμή όταν καλούμε το function, τότε η default τιμή αγνοείται και χρησιμοποιείται η δική μας.
- Εάν, αντίθετα, καλέσουμε το function χωρίς να περάσουμε καμία απολύτως τιμή, τότε το πρόγραμμα δεν θα "χτυπήσει" λάθος, αλλά θα χρησιμοποιήσει αυτόματα την προεπιλεγμένη τιμή.
Στο παρακάτω παράδειγμα δημιουργούμε το function favorite_team(). Θα το καλέσουμε την πρώτη φορά περνώντας τη δική μας τιμή, και μια δεύτερη φορά χωρίς να περάσουμε καμία απολύτως τιμή, για να δούμε τη διαφορά:
app.py
def main():message()favorite_team('Barcelona')favorite_team()def message():print('Everyone has a favorite team')def favorite_team(team='Liverpool'):print('mine is', team)main()
Output
Προαιρετικές Παράμετροι (Optional Parameters)
Πέρα από τις προεπιλεγμένες τιμές, υπάρχουν περιπτώσεις που θέλουμε κάποιες παράμετροι να είναι εντελώς προαιρετικές.
Η λογική είναι απλή: Αν δώσουμε κάποια τιμή κατά την κλήση του function, αυτή θα χρησιμοποιηθεί κανονικά. Αν όχι, το function απλά θα την αγνοήσει και θα συνεχίσει τη δουλειά του.
Για να δηλώσουμε μια προαιρετική μεταβλητή (ειδικά όταν περιμένουμε δεδομένα κειμένου), ο πιο συνηθισμένος τρόπος είναι να τη δηλώσουμε ίση με ένα κενό String (αλφαριθμητικό). Αυτό γίνεται βάζοντας απλά δύο εισαγωγικά χωρίς κανένα χαρακτήρα ανάμεσά τους ("").
Δείτε πώς μπορούμε να φτιάξουμε ένα function που τυπώνει το πλήρες όνομα κάποιου, όπου το μεσαίο όνομα (πατρώνυμο) δεν είναι υποχρεωτικό:
app.py
def main():message()favorite_team('Barcelona')favorite_team()favorite_team('Barcelona', 'Spain')def message():print('Everyone has a favorite team')def favorite_team(team='Liverpool', country=""):if country:print('Your favorite team is {} from {}'.format(team, country))else:print('Your favorite team is {}'.format(team))main()
Output
Ονομαστικές Παράμετροι (Keyword Arguments)
Τέλος, υπάρχει ένας ακόμα εξαιρετικά πρακτικός τρόπος για να περνάμε δεδομένα στα functions: μπορούμε να δηλώσουμε ρητά τα ονόματα των παραμέτρων τη στιγμή που περνάμε τις τιμές μέσα στις παρενθέσεις.
Αυτή η τεχνική (γνωστή και ως keyword arguments) έχει ένα τεράστιο πλεονέκτημα. Μας απελευθερώνει από τον αυστηρό κανόνα της σειράς. Από τη στιγμή που δηλώνουμε σε ποια ακριβώς μεταβλητή απευθύνεται η κάθε τιμή, μπορούμε να περάσουμε τα δεδομένα με οποιαδήποτε σειρά επιθυμούμε, καθώς η Python ξέρει πλέον πού να τα αντιστοιχίσει.
Ας δούμε ένα παράδειγμα για να γίνει απόλυτα κατανοητό:
app.py
def main():message()favorite_team('Barcelona')favorite_team()favorite_team('Barcelona', 'Spain')favorite_team(country='Germany', team='Bayern')def message():print('Everyone has a favorite team')def favorite_team(team='Liverpool', country=""):if country:print('Your favorite team is {} from {}'.format(team, country))else:print('Your favorite team is {}'.format(team))main()
Output
Στηρίξτε την Προσπάθειά μας! ❤️
Αν βρήκατε αυτό το δωρεάν μάθημα χρήσιμο και θέλετε να βοηθήσετε, σκεφτείτε το ενδεχόμενο να κάνετε μια μικρή δωρεά (donation).
Με την πολύτιμη υποστήριξή σας, αυτό το site μπορεί να μεγαλώσει ακόμα περισσότερο, να αναβαθμίσει τις υποδομές του και να αποκτήσει νέες δυνατότητες για την online παράδοση ακόμα περισσότερων δωρεάν μαθημάτων προγραμματισμού για όλους.
Ευχαριστούμε που είστε μέρος της κοινότητάς μας!
full-width


0 Comments
What do you think about Ground of Code?