C είσοδος/έξοδος αρχείων: Διαφορά μεταξύ των αναθεωρήσεων

Περιεχόμενο που διαγράφηκε Περιεχόμενο που προστέθηκε
Η γλώσσα προγραμματισμού C παρέχει μια πρότυπη βιβλιοθήκη με συναρτήσεις για προσπέλαση αρχείων. Αυτές οι συναρτήσεις βρίσκονται στο αρχ...
Ετικέτες: άδειασμα του λήμματος Οπτική επεξεργασία
Αναίρεση έκδοσης 4922120 από τον 194.63.239.233 (Συζήτηση)
Γραμμή 1:
Η γλώσσα προγραμματισμού C παρέχει μια [[πρότυπη βιβλιοθήκη]] με συναρτήσεις για προσπέλαση αρχείων. Αυτές οι συναρτήσεις βρίσκονται στο αρχείο επικεφαλίδας <code><stdio.h></code> <ref>{{cite book | url=http://www.open-std.org/jtc1/sc22/wg14/www/docs/n1124.pdf | title=ISO/IEC 9899:1999 specification | at=p. 274, § 7.19}}</ref>. Αυτή η συλλογή συναρτήσεων προέρχεται από την βιβλιοθήκη "portable I/O package" (=φορητή βιβλιοθήκη συναρτήσεων εισόδου/εξόδου) του Mike Lesk από τα εργαστήρια της Bell αρχές της δεκαετίας του 1970 <ref>{{cite book|last=Kernighan|first=Brian|coauthors=Rob Pike|title=The UNIX Programming Environment|publisher=Prentice Hall|location=Englewood Cliffs|year=1984|page=200}}</ref>.
 
Η λειτουργικότητα εισόδου-εξόδου της C είναι χαμηλού επιπέδου συγκρινόμενη με τα σύγχρονες βιβλιοθήκες. Σήμερα οι λειτουργίες προσπέλασης αρχείων γίνεται με αφαιρετικές δομές ροών δεδομένων (bytes) ''streams'' εισόδου ή εξόδου. Σε αντίθεση με ορισμένες μεταγενέστερες γλώσσες προγραμματισμού η γλώσσα C δεν έχει απευθείας δυνατότητα τυχαίας προσπέλασης αρχείων δεδομένων. Για να διαβαστεί η πληροφορία στο κέντρο του αρχείου ο προγραμματιστής θα πρέπει να δημιουργήσει μια ροή δεδομένων (stream) και στην συνέχεια να προσπελάσει το σημείο αυτό.
 
Το μοντέλο με τις ροές δεδομένων για είσοδο/έξοδο αρχείων έχει χρησιμοποιηθεί στο λειτουργικό σύστημα Unix το οποίο έχει υλοποιηθεί σε γλώσσα προγραμματισμού C. Αρκετά σύγχρονα λειτουργικά συστήματα έχουν κληρονομήσει τις ροές δεδομένων του Unix και πολλές γλώσσες προγραμματισμού της κατηγορίας γλωσσών C έχουν κληρονομήσει την διεπαφή ροών δεδομένων της C (για παράδειγμα η γλώσσα σεναρίων [[PHP]]). Η γλώσσα προγραμματισμού C++ στην πρότυπη βιβλιοθήκη χρησιμοποιεί την ιδέα της ροής δεδομένων στο συντακτικό των βιβλιοθηκών όπως της [[iostream]].
 
== Παρουσίαση των συναρτήσεων ==
 
Οι περισσότερες συναρτήσεις της C για είσοδο/έξοδο βρίσκονται ορισμένες στο αρχείο επικεφαλίδας <code>stdio.h</code> (<code>cstdio</code> είναι το αρχείο επικεφαλίδας στην C++).
 
{| class="wikitable" style="font-size:0.85em"
|-
!
! Χαρακτήρας τύπου<br>Byte<br>
! Χαρακτήρας τύπου<br>Wide
! Περιγραφή
|-
! rowspan=7 | Πρόσβαση αρχείου
| colspan=2 style="text-align:center" | {{anchor|fopen}}<code>[http://code-reference.com/c/stdio.h/fopen fopen]</code>
| ανοίγει ένα αρχείο
|-
| colspan=2 style="text-align:center" | {{anchor|freopen}}<code>[http://code-reference.com/c/stdio.h/freopen freopen]</code>
| ανοίγει ένα διαφορετικό αρχείο χρησιμοποιώντας την ίδια ροή δεδομένων (stream)
|-
| colspan=2 style="text-align:center" | {{anchor|fflush}}<code>[http://code-reference.com/c/stdio.h/fflush fflush]</code>
| συγχρονίζει την έξοδο της ροής δεδομένων με το συγκεκριμένο αρχείο που έχει ανοικτεί
|-
| colspan=2 style="text-align:center" | {{anchor|fclose}}<code>[http://code-reference.com/c/stdio.h/fclose fclose]</code>
| κλείσιμο του αρχείου
|-
| colspan=2 style="text-align:center" | {{anchor|setbuf}}<code>[http://code-reference.com/c/stdio.h/setbuf setbuf]</code>
| ορίζει το ενταμιευτή (buffer) για τη συγκεκριμένη ροή δεδομένων (stream)
|-
| colspan=2 style="text-align:center" | {{anchor|setvbuf}}<code>[http://code-reference.com/c/stdio.h/setvbuf setvbuf]</code>
| ορίζει το ενταμιευτή (buffer) και το μέγεθος της συγκεκριμένης ροής δεδομένων
|-
| colspan=2 style="text-align:center" | {{anchor|fwide}}<code>[http://code-reference.com/c/wchar.h/fwide fwide]</code>
| αλλαγή μεταξύ μιας ροής δεδομένων χαρακτήρων wide εισόδου/εξόδου με μια απλή ροή δεδομένων χαρακτήρων byte
|-
! rowspan=2 | Κατευθείαν <br> είσοδος/έξοδος
| colspan=2 style="text-align:center" | {{anchor|fread}}<code>[http://code-reference.com/c/stdio.h/fread fread]</code>
| διάβασμα από το αρχείο
|-
| colspan=2 style="text-align:center" | {{anchor|fwrite}}<code>[http://code-reference.com/c/stdio.h/fwrite fwrite]</code>
| γράψιμο στο αρχείο
|-
! rowspan=9 | Μη φορμαρισμένη <br> είσοδος/έξοδος
| {{anchor|fgetc|getc}}<code>[http://code-reference.com/c/stdio.h/fgetc fgetc]</code><br><code>[http://code-reference.com/c/stdio.h/getc getc]</code>
| {{anchor|fgetwc|getwc}}<code>[http://code-reference.com/c/wchar.h/fgetwc fgetwc]</code><br><code>[http://code-reference.com/c/wchar.h/getwc getwc]</code>
| διαβάζει ένα byte/<code>wchar_t</code> από μια ροή αρχείου
|-
| {{anchor|fgets}}<code>[http://code-reference.com/c/stdio.h/fgets fgets]</code>
| {{anchor|fgetws}}<code>[http://code-reference.com/c/wchar.h/fgetws fgetws]</code>
| διαβάζει ένα byte/<code>wchar_t</code> συμβολοσειρά (string) από μια ροή αρχείου
|-
| {{anchor|fputc|putc}}<code>[http://code-reference.com/c/stdio.h/fputc fputc]</code><br><code>[http://code-reference.com/c/stdio.h/putc putc]</code>
| {{anchor|fputwc|putwc}}<code>[http://code-reference.com/c/wchar.h/fputwc fputwc]</code><br><code>[http://code-reference.com/c/wchar.h/putwc putwc]</code>
| γράφει ένα byte/<code>wchar_t</code> σε μια ροή αρχείου
|-
| {{anchor|fputs}}<code>[http://code-reference.com/c/stdio.h/fputs fputs]</code>
| {{anchor|fputws}}<code>[http://code-reference.com/c/wchar.h/fputws fputws]</code>
| γράφει ένα byte/<code>wchar_t</code> συμβολοσειρά σε μια ροή αρχείου
|-
| {{anchor|getchar}}<code>[http://code-reference.com/c/stdio.h/getchar getchar]</code>
| {{anchor|getwchar}}<code>[http://code-reference.com/c/wchar.h/getwchar getwchar]</code>
| διαβάζει ένα byte/<code>wchar_t</code> από το stdin (προκαθορισμένη είσοδος - πληκτρολόγιο συνήθως)
|-
| {{anchor|gets}}<code>[http://code-reference.com/c/stdio.h/gets gets]</code>
| μη-διαθέσιμη
| διαβάζει μια συμβολοσειρά bytes από το stdin (αμφισβητήθηκε η χρήση στη C99, είναι ξεπερασμένη στη C11)
|-
| {{anchor|putchar}}<code>[http://code-reference.com/c/stdio.h/putchar putchar]</code>
| {{anchor|putwchar}}<code>[http://code-reference.com/c/wchar.h/putwchar putwchar]</code>
| γράφει ένα byte/<code>wchar_t</code> στο stdout (προκαθορισμένη έξοδος - συνήθως η οθόνη)
|-
| {{anchor|puts}}<code>[http://code-reference.com/c/stdio.h/puts puts]</code>
| μη-διαθέσιμη
| γράφει μια συμβολοσειρά bytes στο stdout
|-
| {{anchor|ungetc}}<code>[http://code-reference.com/c/stdio.h/ungetc ungetc]</code>
| {{anchor|ungetwc}}<code>[http://code-reference.com/c/wchar.h/ungetwc ungetwc]</code>
| τοποθετεί ένα byte/<code>wchar_t</code> πίσω στη ροή δεδομένων του αρχείου
|-
! rowspan=4 | Φορμαρισμένη <br> είσοδος/έξοδος
| {{anchor|scanf|fscanf|sscanf}}<code>[http://code-reference.com/c/stdio.h/scanf scanf]</code><br><code>[http://code-reference.com/c/stdio.h/fscanf fscanf]</code><br><code>[http://code-reference.com/c/stdio.h/sscanf sscanf]</code>
| {{anchor|wscanf|fwscanf|swscanf}}<code>[http://code-reference.com/c/wchar.h/wscanf wscanf]</code><br><code>[http://code-reference.com/c/wchar.h/fwscanf fwscanf]</code><br><code>[http://code-reference.com/c/wchar.h/swscanf swscanf]</code>
| διαβάζει την φορμαρισμένη είσοδο byte/<code>wchar_t</code> από την προκαθορισμένη είσοδο,<br>ροή δεδομένων αρχείου ή ενταμιευτή - buffer
|-
| {{anchor|vscanf|vfscanf|vsscanf}}<code>[http://code-reference.com/c/stdio.h/vscanf vscanf]</code><br><code>[http://code-reference.com/c/stdio.h/vfscanf vfscanf]</code><br><code>[http://code-reference.com/c/stdio.h/vsscanf vsscanf]</code>
| {{anchor|vwscanf|vfwscanf|svwscanf}}<code>[http://code-reference.com/c/stdio.h/vwscanf vwscanf]</code><br><code>[http://code-reference.com/c/wchar.h/vfwscanf vfwscanf]</code><br><code>[http://code-reference.com/c/wchar.h/vswscanf vswscanf]</code>
| διαβάζει την φορμαρισμένη είσοδο byte/<code>wchar_t</code> από την προκαθορισμένη είσοδο stdin,<br>ροή δεδομένων αρχείου ή ένα ενταμιευτή - buffer χρησιμοποιώντας μια μεταβλητή λίστα παραμέτρων
|-
| {{anchor|printf|fprintf|sprintf|snprintf}}<code>[http://code-reference.com/c/stdio.h/printf printf]</code><br><code>[http://code-reference.com/c/stdio.h/fprintf fprintf]</code><br><code>[http://code-reference.com/c/stdio.h/sprintf sprintf]</code><br><code>[http://code-reference.com/c/stdio.h/snprintf snprintf]</code>
| {{anchor|wprintf|fwprintf|swprintf}}<code>[http://code-reference.com/c/wchar.h/wprintf wprintf]</code><br><code>[http://code-reference.com/c/wchar.h/fwprintf fwprintf]</code><br><code>[http://code-reference.com/c/wchar.h/swprintf swprintf]</code>
| τυπώνει φορμαρισμένη byte/<code>wchar_t</code> έξοδο στην προκαθορισμένη έξοδο stdout,<br>ροή δεδομένων ή ένα ενταμιευτή - buffer
|-
| {{anchor|vprintf|vfprintf|vspritf|vsnprintf}}<code>[http://code-reference.com/c/stdio.h/vprintf vprintf]</code><br><code>http://code-reference.com/c/stdio.h/vfprintf vfprintf]</code><br><code>[http://code-reference.com/c/stdio.h/vsprintf vsprintf]</code><br><code>[http://code-reference.com/c/stdio.h/vsnprintf vsnprintf]</code>
| {{anchor|vwprintf|vfwprintf|vswprintf}}<code>[http://code-reference.com/c/wchar.h/vwprintf vwprintf]</code><br><code>[http://code-reference.com/c/wchar.h/vfwprintf vfwprintf]</code><br><code>[http://code-reference.com/c/wchar.h/vswprintf vswprintf]</code>
| τυπώνει την φορμαρισμένη έξοδο byte/<code>wchar_t</code> στην προκαθορισμένη έξοδο stdout,<br>ροή δεδομένων ή ένα ενταμιευτή - buffer χρησιμοποιώντας μεταβλητή λίστα παραμέτρων
|-
! rowspan=5 | Θέση αρχείου
| colspan=2 style="text-align:center" | {{anchor|ftell}}<code>[http://code-reference.com/c/stdio.h/ftell ftell]</code>
| επιστρέφει την τωρινή θέση αρχείου
|-/
| colspan=2 style="text-align:center" | {{anchor|fgetpos}}<code>[http://code-reference.com/c/stdio.h/fgetpos fgetpos]</code>
| παίρνει το δείκτη θέσης αρχείου
|-
| colspan=2 style="text-align:center" | {{anchor|fseek}}<code>[http://code-reference.com/c/stdio.h/fseek fseek]</code>
| μετακίνηση του δείκτη θέσης αρχείου σε μια συγκεκριμένη τοποθεσία στο αρχείο
|-
| colspan=2 style="text-align:center" | {{anchor|fsetpos}}<code>[http://code-reference.com/c/stdio.h/fsetpos fsetpos]</code>
| αλλαγή του δείκτη θέσης αρχείου σε μια συγκεκριμένη θέση στο αρχείο
|-
| colspan=2 style="text-align:center" | {{anchor|rewind}}<code>[http://code-reference.com/c/stdio.h/rewind rewind]</code>
| μετακίνηση του δείκτη θέσης αρχείου στην αρχή του αρχείου
|-
! rowspan=4 | Διαχείριση<br>λαθών
| colspan=2 style="text-align:center" | {{anchor|clearerr}}<code>[http://code-reference.com/c/stdio.h/clearerr clearerr]</code>
| καθαρισμό όλων των μηνυμάτων λαθών
|-
| colspan=2 style="text-align:center" | {{anchor|feof}}<code>[http://code-reference.com/c/stdio.h/feof feof]</code>
| έλεγχος για τέλος αρχείου
|-
| colspan=2 style="text-align:center" | {{anchor|ferror}}<code>[http://code-reference.com/c/stdio.h/ferror ferror]</code>
| έλεγχος για σφάλμα αρχείου
|-
| colspan=2 style="text-align:center" | {{anchor|perror}}<code>[http://code-reference.com/c/stdio.h/perror perror]</code>
| εμφάνισε την συμβολοσειρά που περιγράφει το σφάλμα στην προκαθορισμένη έξοδο λαθών stderr
|-
! rowspan=4 | Operations <br>on files
| colspan=2 style="text-align:center" | {{anchor|remove}}<code>[hhttp://code-reference.com/c/stdio.h/remove remove]</code>
| σβήσιμο ενός αρχείου
|-
| colspan=2 style="text-align:center" | {{anchor|rename}}<code>[http://code-reference.com/c/stdio.h/rename rename]</code>
| μετονομασία αρχείου
|-
| colspan=2 style="text-align:center" | {{anchor|tmpfile}}<code>[http://code-reference.com/c/stdio.h/tmpfile tmpfile]</code>
| επιστρέφει ένα δείκτη στο προσωρινό αρχείο
|-
| colspan=2 style="text-align:center" | {{anchor|tmpnam}}<code>[http://code-reference.com/c/stdio.h/tmpnam tmpnam]</code>
| επιστρέφει ένα μοναδικό όνομα αρχείου
|}
 
== Σταθερές ==
Οι σταθερές οι οποίες είναι ορισμένες στο αρχείο επικεφαλίδας <code>stdio.h</code> περιέχουν:
{| class="wikitable"
|-
! Όνομα !! Σημειώσεις
|-
|<code>EOF</code> || ένας αρνητικός ακέραιος τύπου <code>int</code> ο οποίος χρησιμοποιείται για να δείξει την συνθήκη τέλους αρχείου (end-of-file EOF)
|-
|<code>[http://c-p-p.net/c/stdio.h/bufsiz BUFSIZ]</code> || ένας ακέραιος ο οποίος δείχνει το μέγεθος του ενταμιευτή - buffer ο οποίος χρησιμοποιείται από την συνάρτηση <code>setbuf()</code>
|-
|<code>FILENAME_MAX</code> || το μέγεθος του πίνακα τύπου <code>char</code> ο οποίος είναι αρκετά μεγάλος για να αποθηκεύσει το κάθε όνομα αρχείου το οποίο δύναται να ανοιχθεί
|-
|<code>FOPEN_MAX</code> || ο αριθμός των αρχείων τα οποία μπορούν να ανοίξουν συγχρόνως - τουλάχιστον 8 πρέπει να είναι η τιμή
|-
|<code>_IOFBF</code> || συντομογραφία του "input/output fully buffered" (είσοδος/έξοδος συνεχή με χρήση ενταμιευτή-buffer) - είναι ένας ακέραιος αριθμός ο οποίος περνάει ως παράμετρος στην συνάρτηση <code>setvbuf()</code> ώστε να γίνει αίτημα για ''block buffered'' (με μπλοκ ενταμιευτή) εισόδου για μια ανοικτή ροή δεδομένων (stream)
|-
|<code>_IOLBF</code> || μια συντομογραφία για το "input/output line buffered" (γραμμή εισόδου/εξόδου ενταμιευτή) - είναι ένας ακέραιος αριθμός ο οποίος μπορεί να περάσει ως παράμετρος στη συνάρτηση <code>setvbuf()</code> για να γίνει αίτημα ''line buffered'' (γραμμής ενταμιευτή) εισόδου και εξόδου για μια ανοικτή ροή δεδομένων (stream)
|-
|<code>_IONBF</code> || μια συντομογραφία του "input/output not buffered" (είσοδος/έξοδος χωρίς ενταμιευτή-buffer) - είναι ένας ακέραιος αριθμός ο οποίος μπορεί να περάσει ως παράμετρος στην συνάρτηση <code>setvbuf()</code> για να γίνει αίτημα ''unbuffered'' (χωρίς ενταμιευτή) εισόδου/εξόδου για μια ανοικτή ροή δεδομένων (stream)
|-
|<code>L_tmpnam</code> || το μέγεθος ενός πίνακα τύπου <code>char</code> ο οποίος είναι αρκετά μεγάλος για να αποθηκεύει το προσωρινό όνομα αρχείου που δημιουργείται από την συνάρτηση <code>tmpnam()</code>
|-
|<code>NULL</code> || ένα μάκρο σε μια κενή σταθερά "null pointer" - είναι μια σταθερά που αντιπροσωπεύει ένα δείκτη οποίος σε καμία περίπτωση δεν είναι αντικείμενο μέσα στην μνήμη του υπολογιστή
|-
|<code>SEEK_CUR</code> || ένας ακέραιος ο οποίος μπορεί να περάσει ως παράμετρος στη συνάρτηση <code>fseek()</code> για να γίνει αίτημα σχετικής θέσης στο αρχείο από την τωρινή θέση
|-
|<code>SEEK_END</code> || ένας ακέραιος ο οποίος μπορεί να περάσει ως παράμετρος στην συνάρτηση <code>fseek()</code> για να γίνει αίτημα σχετικής θέσης σε σχέση με το τέλος του αρχείου
|-
|<code>SEEK_SET</code> || ένας ακέραιος ο οποίος μπορεί να περάσει ως παράμετρος στην συνάρτηση <code>fseek()</code> για να γίνει αίτημα σχετικής θέσης σε σχέση με την αρχή του αρχείου
|-
|<code>TMP_MAX</code> || ο μέγιστος αριθμός μοναδικών ονομάτων που μπορούν να δημιουργηθούν από την συνάρτηση <code>tmpnam()</code> - η τιμή πρέπει να είναι τουλάχιστον 25
|}
 
==Μεταβλητές==
Οι μεταβλητές οι οποίες ορίζονται στο αρχείο επικεφαλίδας <code>stdio.h</code> περιέχουν:
{| class="wikitable"
|-
! Όνομα !! Σημειώσεις
|-
|<code>stdin</code> || ένας δείκτης σε ένα αρχείο <code>FILE</code> το οποίο αναφέρεται στην προκαθορισμένη είσοδο του συστήματός (συνήθως είναι το πληκτρολόγιο).
|-
|<code>stdout</code> || ένας δείκτης σε ένα αρχείο <code>FILE</code> το οποίο αναφέρεται στην προκαθορισμένη έξοδο του συστήματός (συνήθως είναι το τερματικό της οθόνης).
|-
|<code>stderr</code> || ένας δείκτης σε ένα αρχείο <code>FILE</code> το οποίο αναφέρεται στην προκαθορισμένη έξοδο σφαλμάτων του συστήματός (συνήθως είναι το τερματικό της οθόνης).
|}
 
== Τύποι δομών δεδομένων==
Δομές δεδομένων οι οποίες ορίζονται μέσα στο αρχείο επικεφαλίδας <code>stdio.h</code> περιέχουν:
* <code>[http://c-p-p.net/c/keywords/file FILE]</code> - μια δομή δεδομένων η οποία περιέχει πληροφορίες για το αρχείο ή την ροή δεδομένων (κειμένου) που χρειάζεται για να γίνουν οι λειτουργίες εισόδου εξόδου:
** μια περιγραφή του αρχείου
** θέση μέσα της ροής δεδομένων
** επισήμανση τέλους αρχείου (end-of-file)
** επισήμανσης λάθους
** δείκτης στην ροή δεδομένων του buffera
* <code>fpos_t</code> - μια δομή η οποία δεν έχει την μορφή πίνακα η οποία έχει την δυνατότητα να αναγνωρίζονται οι θέσεις του κάθε byte μέσα στο αρχείο.
* <code>size_t</code> - ένας ακέραιος χωρίς πρόσημο (unsigned integer) ο οποίος περιέχει το αποτέλεσμα της συνάρτησης <code>[[sizeof]]</code>.
 
==Παράδειγμα ==
Ο παρακάτω κώδικας προγραμματισμού στην γλώσσα C ανοίγει ένα δυαδικό αρχείο ''myfile'', διαβάζει πέντε bytes, τα εμφανίζει στην οθόνη και στην συνέχεια κλείνει το αρχείο.
 
<source lang="c">
#include <stdio.h>
#include <stdlib.h> // για ορισμούς των EXIT_FAILURE και EXIT_SUCCESS
 
int main(void) {
char buffer[5] = {0}; /* αρχικοποίηση του πίνακα με μηδενικά */
int i, rc;
FILE *fp = fopen("myfile", "rb");
 
if (fp == NULL) {
// το λάθος αυτό παρουσιάζεται όταν δεν υπάρχει το αρχείο myfile
perror("Λάθος στο άνοιγμα του αρχείου \"myfile\"");
// το μήνυμα που εμφανίζεται συμπληρωμένο από την perror είναι:
// "Λάθος στο άνοιγμα του αρχείου "myfile": No such file or directory"
return EXIT_FAILURE;
}
 
for (i = 0; (rc = getc(fp)) != EOF && i < 5; buffer[i++] = rc) { }
fclose(fp);
 
if (i == 5) {
puts("Τα παρακάτω bytes διαβάστηκαν...");
printf("%x %x %x %x %x\n", buffer[0], buffer[1], buffer[2], buffer[3], buffer[4]);
}
else
// το σφάλμα αυτό παρουσιάζεται όταν το αρχείο είναι μικρότερο από 5 bytes
fputs("Ένα σφάλμα προέκυψε στο διάβασμα του αρχείου.\n", stderr);
 
return EXIT_SUCCESS;
}
</source>
 
==Παραπομπές==
{{παραπομπές}}
 
{{ενσωμάτωση κειμένου|en|C file input/output}}
 
==Άλλες πηγές==
* [http://code-reference.com/c/stdio.h stdio.h on Coding Programmer Page / C Library Reference and Examples] (en)
 
 
[[Κατηγορία:C]]